XGM Forum
Сайт - Статьи - Проекты - Ресурсы - Блоги

Форуме в режиме ТОЛЬКО ЧТЕНИЕ. Вы можете задать вопросы в Q/A на сайте, либо создать свой проект или ресурс.
Вернуться   XGM Forum > Warcraft> Академия: форум для вопросов> Jass
Ник
Пароль
Войти через VK в один клик
Сайт использует только имя.

Закрытая тема
 
FKoFF
Venomancer 89lvl. Europe
offline
Опыт: 5,975
Активность:
Война с утечками
Недавно убрал из кода запуск таймеров через луп, некоторое количество лишних локалок осталось покачто в коде - уберу позже. Однако где то есть утечки хэндлов - где - не могу сообразить. Прошу знающих людей прочитать код и сказать где же я недоглядел.
function Trig_Spell_RalRune_Conditions takes nothing returns boolean
    if ( not ( GetSpellAbilityId() == 'A00E' ) ) then
        return false
    endif
    return true
endfunction


function MatchingFiresoulsConditions takes nothing returns boolean
return IsUnitAlly(GetFilterUnit(), GetOwningPlayer(udg_U_Cookie)) != true and GetUnitState(GetFilterUnit(),UNIT_STATE_LIFE) > 0 and IsUnitType(GetFilterUnit(), UNIT_TYPE_STRUCTURE) == false 
endfunction


function Unit_Firsouls_Temp_Group takes nothing returns nothing
    call GroupAddUnitSimple( GetEnumUnit(), udg_Temp_Group )
endfunction

function ExplodeFireSoul takes nothing returns nothing
local unit u = udg_U_Cookie
local unit v = GetEnumUnit()
local integer lvl = GetUnitAbilityLevel(u, 'A00E') 
local real constantdmg = 10*lvl
local real constantburndmg =  2*lvl
local real constantburnsec =  5 
call MakeEleDamage(u, v, constantdmg, 2)
call BurnUnit(v, u, constantburndmg, constantburnsec)
set u = null
set v = null
set constantdmg = 0
set constantburndmg = 0
set constantburnsec = 0
set lvl = 0
endfunction


function MoveFireSouls takes nothing returns nothing
local timer t = GetExpiredTimer()
local integer i = GetHandleId(t)
local unit u = LoadUnitHandle(udg_Data, i, 1)
local real angle = LoadReal(udg_Data, i, 2)
local integer right = LoadInteger(udg_Data, i, 4)
local real x1 = LoadReal(udg_Data, i, 5)
local real y1 = LoadReal(udg_Data, i, 6)
local real x = GetUnitX(u)
local real y = GetUnitY(u)             
local real dist = LoadReal(udg_Data, i, 3)
local real array temp
local real constantdist = 0
local real atf = 0
local unit caster = LoadUnitHandle(udg_Data, i, 7)
local location target = Location(x1,y1)
local location curpos = Location(x,y)

if (GetUnitUserData(u) == 0)then
set temp[1] = DistanceBetweenPoints(curpos, target)
set temp[2] = AngleBetweenPoints(curpos, target)

if ( right == 1 ) then

set temp[3] = (temp[2] -  (temp[1]/20))
else
set temp[3] = (temp[2] + (temp[1]/20))
endif

if ( temp[3] > (temp[2] + 100)) then
set temp[3] = temp[2] + 100
else
endif

if ( temp[3] < (temp[2] - 100)) then
set temp[3] = temp[2] - 100
else
endif

set constantdist = temp[1]/5

set x = x + constantdist * Cos(temp[3] * bj_DEGTORAD)
set y = y + constantdist * Sin(temp[3] * bj_DEGTORAD)
call MoveLocation(curpos, x, y)

call SetUnitPositionLoc(u, curpos)

if (DistanceBetweenPoints(curpos, target) <= 10) then
if (GetUnitUserData(u) == 0)then
set udg_U_Cookie = caster
set bj_wantDestroyGroup = true 
call ForGroupBJ( GetUnitsInRangeOfLocMatching(80.00, curpos, Condition(function MatchingFiresoulsConditions)), function ExplodeFireSoul )
call SetUnitUserData(u,1)
call KillUnit(u)
call DestroyTimer(t)
call FlushChildHashtable(udg_Data, i)
else
endif
else
endif

else
endif



set i = 0
set t = null
set u = null
set angle = 0
set x = 0
set y = 0
set dist = 0
set temp[1] = 0
set temp[2] = 0
set temp[3] = 0
set atf = 0
set right = 0
set constantdist = 0
call RemoveLocation(curpos)
call RemoveLocation(target)
endfunction

function SetFireSoul takes unit owner, unit missle, real angle, location p, integer lvl, integer i4 returns nothing
local timer t = CreateTimer()
local location p1 = Location(GetUnitX(owner), GetUnitY(owner))
local real tempdist = DistanceBetweenPoints(p1,p)
local real tempdist1 = tempdist/4
local integer i1 = R2I(tempdist1)
local integer i2 = 1
local real array temp
local integer hi = 0
local integer i3 = 0
set temp[2] = DistanceBetweenPoints(p1, p)
set tempdist = 0
set temp[3] = temp[2] / ( temp[2] / 25 )
set i1 = R2I(temp[3])


if ( i4 == 1 ) then
set i3 = 0
else
set i3 = 1
endif



set hi = GetHandleId(t)
call SaveUnitHandle(udg_Data, hi, 1, missle)
call SaveReal(udg_Data, hi, 2, angle)
call SaveReal(udg_Data, hi, 3, temp[2])
call SaveReal(udg_Data, hi, 5, GetLocationX(p))
call SaveReal(udg_Data, hi, 6, GetLocationY(p))
call SaveUnitHandle(udg_Data, hi, 7, owner)
call SaveInteger(udg_Data, hi, 4, i3)  
call TimerStart(t, 0.03, true, function MoveFireSouls)
set t = null

call UnitApplyTimedLife(missle, 'BTLF' ,((I2R(i2)*0.03)+0.6))


set i1 = 0
set i2 = 0
set temp[1] = 0
set temp[3] = 0
set temp[2] = 0
set hi = 0
call RemoveLocation(p)
call RemoveLocation(p1)
set i3 = 0
set i4 = 0
set owner = null
set missle = null
endfunction

function SpawnFS takes nothing returns nothing
local timer t = GetExpiredTimer()
local integer i = GetHandleId(t)
local unit u = LoadUnitHandle(udg_Data,i, 1)
local real x = LoadReal(udg_Data, i, 3)
local real y = LoadReal(udg_Data, i, 4)
local rect rec = Rect((x-80),(y-80), (x+80), (y+80))
local location p = GetRandomLocInRect(rec)
local location p1 = Location(GetUnitX(u), GetUnitY(u))
local integer lvl = LoadInteger(udg_Data, i, 5)
local real angle = AngleBetweenPoints(p1, p)
local integer i4 = LoadInteger(udg_Data, i, 6)
local unit u1 = CreateUnitAtLoc( GetOwningPlayer(u), 'h002', p1, bj_UNIT_FACING )

call SetFireSoul(u, u1, AngleBetweenPoints(p1, p), p, lvl, i4) 
call RemoveLocation(p)
call RemoveLocation(p1)
call FlushChildHashtable(udg_Data, i)
call DestroyTimer(t)

set u1 = null
set u = null
set lvl = 0
set angle = 0
set x = 0
set y = 0
set i4 = 0
call RemoveRect(rec)
endfunction


function SpawnFireSouls takes unit caster, integer lvl, real x1, real y1 returns nothing
local timer array t
local integer const = 10+(10*lvl)
local integer i = 1
local integer i3 = 0



loop
exitwhen i > const
set t[i] = CreateTimer()
if ( i3 == 1 ) then
set i3 = 0
else
set i3 = 1
endif
call SaveUnitHandle(udg_Data,GetHandleId(t[i]), 1, caster)
call SaveInteger(udg_Data, GetHandleId(t[i]), 2, lvl)
call SaveReal(udg_Data, GetHandleId(t[i]), 3, x1)
call SaveReal(udg_Data, GetHandleId(t[i]), 4, y1)
call SaveInteger(udg_Data,GetHandleId(t[i]), 5, lvl)
call SaveInteger(udg_Data,GetHandleId(t[i]), 6, i3)
call TimerStart(t[i], 0.2*I2R(i), false, function SpawnFS)
set t[i] = null
set i = i+1
endloop

  
set i = 0
set i3 = 0
set const = 0
endfunction

function Trig_Spell_RalRune_Actions takes nothing returns nothing
    local unit u = GetTriggerUnit()
    local integer i = 1
    local integer lvl = GetUnitAbilityLevel(u, GetSpellAbilityId())
    local location p = Location(GetUnitX(u), GetUnitY(u))
    local location p1 = GetSpellTargetLoc()

    loop
        exitwhen ( IsUnitInGroup(GetTriggerUnit(), udg_CASTING_GROUP) != true )
        call TriggerSleepAction(RMaxBJ(bj_WAIT_FOR_COND_MIN_INTERVAL, 0.10))
    endloop

    if ( GetUnitUserData(GetTriggerUnit()) <= 0 ) then
        call SpawnFireSouls(u, lvl, GetLocationX(p1), GetLocationY(p1))

    else
    endif
    set u = null
    call RemoveLocation(p)
    call RemoveLocation(p1)
    set i = 0
    set lvl = 0
endfunction

//===========================================================================
function InitTrig_Spell_RalRune takes nothing returns nothing
    set gg_trg_Spell_RalRune = CreateTrigger(  )
    call TriggerRegisterAnyUnitEventBJ( gg_trg_Spell_RalRune, EVENT_PLAYER_UNIT_SPELL_EFFECT )
    call TriggerAddCondition( gg_trg_Spell_RalRune, Condition( function Trig_Spell_RalRune_Conditions ) )
    call TriggerAddAction( gg_trg_Spell_RalRune, function Trig_Spell_RalRune_Actions )
endfunction
MakeEleDamage и BurnUnit - функции из другой оперы. Функция вызывает утечки независимо от того, есть ли хоть какое то количество юнитов рядом.
P.S острить по поводу бж в некоторых местах - не надо. И да, я знаю что код не самый читабельный или чистый.
Старый 17.11.2010, 05:36
FKoFF
Venomancer 89lvl. Europe
offline
Опыт: 5,975
Активность:
при установке количества мисслов на 1200 (максимальное количество которое будет за 40 минут игры при откате в 20 секунд и количестве мисслов 2+2*лвл) игра не вылетела и не залагала, однако на вес процесса по окончанию бомбежки вырос на 30 000 кб
после 7 запусков (1200 мисслов). не прошло и 10% времени как вес процесса увеличился на дополнительные 79 000 кб.
Где утечки?
количество хэндлов на тестовой карте = 1049000
после проверки с 7 запусками количество хендлов на момент дикого лага(25%) = 2хххххх и стремительно растет
Старый 17.11.2010, 15:06
darkVader

offline
Опыт: 197
Активность:
Цитата:
Сообщение от FKoFF
острить по поводу бж в некоторых местах - не надо


а я буду=))) некотрые бж функции используют хэндл локалки которые в итоге не обнуляются, вот пример
строка:
call ForGroupBJ( GetUnitsInRangeOfLocMatching(80.00, curpos, Condition(function MatchingFiresoulsConditions)), function ExplodeFireSoul )

и утечная функция
function GetUnitsInRangeOfLocMatching takes real radius, location whichLocation, boolexpr filter returns group
local group g = CreateGroup()
call GroupEnumUnitsInRangeOfLoc(g, whichLocation, radius, filter)
call DestroyBoolExpr(filter)
return g
endfunction

тут хэндл не обнуляется и дальше по коду у тебя эта группа не разрушается
дальше код не смотрел, думаю если и есть то примерно то же самое
Старый 29.11.2010, 07:20
JassMan
свободен
offline
Опыт: 4,193
Активность:
Исправь хоть что-то и выложи сюда, а я уже сам в обед зайду и перепишу код нормально
Старый 29.11.2010, 08:21
FKoFF
Venomancer 89lvl. Europe
offline
Опыт: 5,975
Активность:
да уже исправил, после полной работы сценария 15 утечек - не страшно.
Старый 29.11.2010, 22:26
Закрытая тема

Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск

Ваши права в разделе
Вы не можете создавать темы
Вы не можете отвечать на сообщения
Вы не можете прикреплять файлы
Вы можете скачивать файлы

BB-коды Вкл.
[IMG] код Вкл.
HTML код Выкл.
Быстрый переход



Часовой пояс GMT +3, время: 00:20.