Ë
    g^(h9,  ã                   ó†  — d dl Z d dlZd dlmZ d dlmZ d dlmZmZ d dl	m
Z
 	 d dlmZmZmZmZmZmZmZmZmZmZ  e j0                  e«      Zej7                  e j8                  «       	 	 	 dded	ed
edeee       deee       de!e"e ef   eef   fd„Z# G d„ de«      Z$de
d	edee   fd„Z%y# e$ rZ ed«      e‚dZ[ww xY w)é    N)ÚIntEnum)ÚOptional)ÚGraphÚis_submodule)ÚSACStats)
ÚlpDotÚ	LpIntegerÚ
LpMaximizeÚ
LpMinimizeÚ	LpProblemÚLpStatusÚlpSumÚ
LpVariableÚPULP_CBC_CMDÚvaluezBPlease install pulp package. See: https://github.com/coin-or/pulp.ÚgraphÚmemory_budgetÚ
world_sizeÚac_unitsÚ
fsdp_unitsÚreturnc                 óª  ‡ ‡%— t        ‰ j                  «      }d}d}t        dt        «      }t	        j
                  dt        t        |«      «      ddt        «      }	t	        j
                  dt        t        |«      «      dd«      }
t	        j
                  dt        t        |«      «      d«      }t	        j
                  d	t        t        |«      «      d«      }t	        j
                  d
t        t        |«      «      d«      }t	        j
                  dt        t        |«      «      d«      }t	        j
                  dt        t        |«      «      d«      }t	        dd«      }|r;t        |«      }t        |«      D ]"  Š%‰ j                  ‰%   d   |vsŒ||	‰%   dk(  z  }Œ$ |r1t        |«      D ]#  Š%t        ˆ ˆ%fd„|D «       «      sŒ||	‰%   dk(  z  }Œ% t        |«      D ]=  Š%t        ‰%dz   |«      D ])  }‰ j                  ‰%   |   dk(  sŒ||	‰%   |	|   z   dk  z  }Œ+ Œ? t        |«      D ]   Š%‰ j                  ‰%   d   sŒ||	‰%   dk(  z  }Œ" t        |«      D �]?  Š%‰ j                  ‰%   d   sã‰ j                  ‰%   d   ‰ j                  ‰%   d   k  r¾t        j                  d‰ j                  ‰%   d   «       t        j                  d‰ j                  ‰%   d   «       t        j                  d‰ j                  ‰%   d   «       t        j                  d«       t        j                  d«       ‰ j                  ‰%   d   ‰ j                  ‰%   d<   ‰ j                  ‰%   d   |z  }‰ j                  ‰%   d   |z  }||‰%   ||
‰%   z  ||z
  |	‰%   z  z
  k(  z  }�ŒB t        |«      D ]d  Š%||	‰%   |
‰%   k\  z  }‰ j                  ‰%   d   rŒ$‰ j                  ‰%   d   |z  }‰ j                  ‰%   d   |z  }||
‰%   ||z
  |z  |	‰%   z  k\  z  }Œf t        |«      D ]“  Š%‰ j                  ‰%   d   |z  }‰ j                  ‰%   d   |z  }‰ j                  ‰%   d   }dg|z  }t        |«      D ]&  }‰ j                  ‰ j                  |      d   }d||<   Œ( ||‰%   ||z   t!        ||«      z
  k(  z  }Œ• ‰ j                  d   d   |z  }t        |«      D ].  Š%‰ j                  ‰%   d   |z  }||‰%   |‰%   ||z   |z  z   k(  z  }Œ0 t        |«      D ]  Š%|||‰%   k\  z  }Œ t        |«      D ]`  Š%t        ‰ j                  ‰%   d   «      D ]@  }‰ j                  ‰%   d   |   }‰ j                  ‰%   d    |   }||‰%   ||
‰%   z  |z   k\  z  }ŒB Œb t        |«      D ]S  Š%‰ j                  ‰%   d!   }||‰%   ||	‰%   z  k  z  }||‰%   ||‰%   z  k  z  }||‰%   ||‰%   z  |d|	‰%   z
  z  z
  k\  z  }ŒU |||k  z  }|t#        |«      z  }t%        d"d#d¬$«      } |j'                  | «      }!|!dk7  r"t        j)                  d%t*        |!   «       i dd&fS i }"t        |«      D ]J  Š%t-        |	‰%   j.                  «      dk(  sŒt-        |
‰%   j.                  d'«      |"‰ j                  ‰%   d   <   ŒL t-        t1        |j2                  «      d(«      }#t-        |j.                  |z  «      }$|"|#|$fS ))a6  
    MILP to decide which modules to AC and how much memory to discard.
    The objective is to minimize recomputation time.
    The constraint is to ensure peak memory is under budget.

    Args:
        graph: graph representation of the model as a module submodule tree
            where each node is a submodule with memory & runtime stats
        memory_budget: memory budget in GiB
        world_size: number of GPUs. In the case of FSDP, world_size will be
            used to compute the amount of parameter and gradient memory on each rank
        ac_units: a list of user-specified AC units.
        fsdp_units: a list of FSDP units. AC units cannot be supermodules of FSDP units.

    Returns:
        Dict[str, float]: the optimal SAC solution, mapping from module fqn to
            the percentage of activation memory to **discard**
        float: the recomputation time of the optimal SAC solution
        int: upper bound on the peak memory of the optimal SAC solution.
            note that value of -1 means that the ILP solver failed to find a solution.

    éd   i   @ÚSACÚyr   é   ÚrÚdÚaÚmÚrcpÚrctÚmax_mÚfqnc              3   óV   •K  — | ]   }t        |‰j                  ‰   d    «      –— Œ" y­w)r$   N)r   Únodes)Ú.0Ú	fsdp_unitr   Úis     €€ú^/var/www/skyplay_api_hub/venv/lib/python3.12/site-packages/torch/distributed/_tools/sac_ilp.pyú	<genexpr>zsac_milp.<locals>.<genexpr>d   s-   øè ø€ ò àô ˜Y¨¯©°A©°uÑ(=×>ñùs   ƒ&)Úis_leafÚ
sac_memoryÚact_fw_per_modulezFor module {%s}: z.activation memory from memory tracker is {%d},z-activation memory from SAC estimator is {%d}.z!Something is wrong. Please check!z&Overriding the latter with the former.Úact_grad_per_moduleÚ	act_totalÚpos_fw_post_orderÚindexÚparam_per_moduleÚ
grad_totalÚ
n_segmentsÚslopesÚ
interceptsÚsac_runtimeçš™™™™™©?é´   ©ÚgapRelÚ	timeLimitÚmsgú$Solver failed to find a solution: %séÿÿÿÿé   é   )Úlenr&   r   r   r   ÚmatrixÚlistÚranger	   ÚsetÚanyÚ	ad_matrixÚloggerÚwarningÚ	name2nodeÚfw_post_orderr   r   r   ÚsolveÚerrorr   ÚroundÚvarValuer   Ú	objective)&r   r   r   r   r   Ú	num_nodesÚMÚMEM_MULTIPLIERÚprobr   r   r   r   r    r!   r"   r#   Úac_units_setÚjÚACM_iÚIA_iÚAG_iÚTA_iÚposÚcoeffÚpÚP_1ÚTG_iÚsÚslopeÚ	interceptÚACT_iÚsolverÚstatusÚac_decisionsÚrecomputation_timeÚpeak_memr)   s&   `                                    @r*   Úsac_milprk   #   sj  ù€ ô: �E—K‘KÓ €IØ€AØ€Nô �UœJÓ'€Dô 	×Ñ˜#œt¤E¨)Ó$4Ó5°q¸!¼YÓG€Aä×Ñ˜#œt¤E¨)Ó$4Ó5°q¸!Ó<€Aä×Ñ˜#œt¤E¨)Ó$4Ó5°qÓ9€Aä×Ñ˜#œt¤E¨)Ó$4Ó5°qÓ9€Aä×Ñ˜#œt¤E¨)Ó$4Ó5°qÓ9€Aä
×
Ñ
˜E¤4¬¨iÓ(8Ó#9¸1Ó
=€Cä
×
Ñ
˜E¤4¬¨iÓ(8Ó#9¸1Ó
=€Cä�w Ó"€Eñ Ü˜8“}ˆÜ�yÓ!ò 	"ˆAØ�{‰{˜1‰~˜eÑ$¨LÒ8Ø˜˜!™ ™	Ñ!‘ð	"ñ
 Ü�yÓ!ò 	"ˆAÜô à!+ôõ ð ˜˜!™ ™	Ñ!‘ð	"ô �9Óò )ˆÜ�q˜1‘u˜iÓ(ò 	)ˆAØ�‰˜qÑ! !Ñ$¨Ó)Ø˜˜!™˜q ™t™ qÑ(Ñ(‘ñ	)ð)ô �9Óò ˆØ�;‰;�q‰>˜)Ó$Ø�A�a‘D˜A‘IÑ‰Dðô
 �9Óó =ˆð —‘˜A‘˜yÒ)¨u¯{©{¸1©~Øñ0
à�K‰K˜‰NÐ.Ñ/ò00ô �N‰NÐ.°·±¸A±¸uÑ0EÔFÜ�N‰NØ@Ø—‘˜A‘Ð2Ñ3ôô �N‰NØ?Ø—‘˜A‘˜|Ñ,ôô �N‰NÐ>Ô?Ü�N‰NÐCÔDØ+0¯;©;°q©>Ð:MÑ+NˆE�K‰K˜‰N˜<Ñ(Ø—‘˜A‘˜|Ñ,¨~Ñ=ˆØ�{‰{˜1‰~Ð1Ñ2°^ÑCˆØ��!‘˜  !¡™¨°©¸¸!¹Ñ'<Ñ<Ñ<Ñ<Šð/=ô< �9Óò 6ˆØ��!‘˜˜!™‘ÑˆØ�;‰;�q‰>˜)Ò$ØØ—‘˜A‘˜|Ñ,¨~Ñ=ˆØ�{‰{˜1‰~Ð1Ñ2°^ÑCˆØ��!‘˜ ™¨Ñ.°°1±Ñ5Ñ5Ñ5‰ð6ô �9Óò 	6ˆØ�{‰{˜1‰~Ð3Ñ4°~ÑEˆØ�{‰{˜1‰~˜kÑ*¨^Ñ;ˆà�k‰k˜!‰nÐ0Ñ1ˆØ��i‘ˆÜ�s“ò 	ˆAØ—‘ × 3Ñ 3°AÑ 6Ñ7¸Ñ@ˆAØˆE�!ŠHð	ð 	��!‘˜˜t™¤e¨E°1£oÑ5Ñ5Ñ5‰ð	6ð �+‰+�a‰.Ð+Ñ
,¨~Ñ
=€CÜ�9Óò 9ˆØ�{‰{˜1‰~˜lÑ+¨nÑ<ˆØ��!‘˜˜!™  d¡
¨jÑ8Ñ8Ñ8Ñ8‰ð9ô
 �9Óò ˆØ�˜˜1™‘Ñ‰ðô �9Óò 7ˆÜ�u—{‘{ 1‘~ lÑ3Ó4ò 	7ˆAØ—K‘K ‘N 8Ñ,¨QÑ/ˆEØŸ™ A™ |Ñ4°QÑ7ˆIØ�C˜‘F˜e a¨¡d™l¨YÑ6Ñ6Ñ6‰Dñ	7ð7ô �9Óò :ˆØ—‘˜A‘˜}Ñ-ˆØ��A‘˜!˜a ™d™(Ñ"Ñ"ˆØ��A‘˜% # a¡&™.Ñ(Ñ(ˆØ��A‘˜% # a¡&™.¨1°°A°a±D±©>Ñ9Ñ9Ñ9‰ð	:ð 	ˆE�]Ñ"Ñ"€Dð 	ŒE�#‹JÑ€Dô  °¸!Ô<€FØ�Z‰Z˜Ó€Fð �‚{Ü�‰Ð;¼XÀfÑ=MÔNØ�1�bˆyÐð €LÜ�9Óò JˆÜ��1‘—‘Ó 1Ó$Ü27¸¸!¹¿¹ÀqÓ2IˆL˜Ÿ™ Q™¨Ñ.Ò/ðJô œu T§^¡^Ó4°aÓ8ÐÜ�U—^‘^ nÑ4Ó5€HàÐ+¨XÐ5Ð5ó    c                   ó   — e Zd ZdZdZy)ÚSACDecisionr   r   N)Ú__name__Ú
__module__Ú__qualname__Ú	RECOMPUTEÚSAVE© rl   r*   rn   rn   Ü   s   „ Ø€IØ�Drl   rn   Ú	sac_statsc                 óˆ  — d|cxk  rdk  sn t        d|› d�«      ‚t        | j                  «      }t        dt        «      }t        j                  dt        t        |«      «      ddt        «      }| j                  r5| j                  D ]%  }|||   t        j                  j                  k(  z  }Œ' n<t        | j                  dd | j                  dd «      D ]  \  }}|||   ||   k(  z  }Œ | j                   D ]%  }|||   t        j"                  j                  k(  z  }Œ' | j$                  D ]<  \  }}	||	k7  r|||   ||	   k(  z  }Œ|||   t        j                  j                  k(  z  }Œ> t'        j(                  |t+        | j,                  «      z  «      }
|t/        || j,                  «      |
k  z  }|t/        || j0                  «      z  }t3        d	d
d¬«      }|j5                  |«      }|dk7  rt6        j9                  dt:        |   «       g S t        |«      D �cg c]  }t=        ||   j>                  «      ‘Œ c}S c c}w )aB  
    This is adapted from --
    https://github.com/facebookresearch/xformers/blob/c6c0ac31f1b08542a0bc27278c6ed10f825f6963/xformers/checkpoint.py#L375

    Given the SACStats of a module, including list of operators, their memory, runtimes, and metadata,
    decide via MILP an optimal set of operators to checkpoint under a given ``memory_budget``.

    Args:
        sac_stats: the SACStats object of the module
        memory_budget: a float between zero and one

    Returns:
        List[int]: the decision whether each operator should be saved (1) or recomptued (0).
    r   r   z5`memory_budget` must be a float between 0 and 1. Got ú.zSAC-per-moduleÚxNr@   r9   é
   r;   r?   ) Ú
ValueErrorrC   Ú
func_namesr   r
   r   rD   rE   rF   r	   Úforce_store_randomÚrand_opsrn   rs   r   ÚzipÚview_like_opsrr   Úinplace_opsÚmathÚceilÚsumÚmemoryr   Úruntimesr   rN   rJ   rO   r   rP   rQ   )ru   r   Únum_opsrV   rx   r)   Úi1Úi2ÚopÚ	op_parentÚ
max_memoryrf   rg   s                r*   Ú+get_optimal_checkpointing_policy_per_modulerŒ   á   sD  € ð" �Ô# !Ô#ÜØCÀMÀ?ÐRSÐTó
ð 	
ô �)×&Ñ&Ó'€Gô Ð%¤zÓ2€Dô 	×Ñ˜#œt¤E¨'£NÓ3°Q¸¼9ÓE€Að
 ×#Ò#Ø×#Ñ#ò 	3ˆAØ�A�a‘DœK×,Ñ,×2Ñ2Ñ2Ñ2‰Dñ	3ô ˜)×,Ñ,¨S¨bÐ1°9×3EÑ3EÀaÀbÐ3IÓJò 	#‰FˆB�Ø�A�b‘E˜Q˜r™U‘NÑ"‰Dð	#ð ×$Ñ$ò 4ˆØ��!‘œ×-Ñ-×3Ñ3Ñ3Ñ3‰ð4ð #×.Ñ.ò 4‰ˆˆIØ�Š?Ø�A�b‘E˜Q˜y™\Ñ)Ñ)‰Dà�A�b‘Eœ[×-Ñ-×3Ñ3Ñ3Ñ3‰Dð	4ô —‘˜=¬3¨y×/?Ñ/?Ó+@Ñ@ÓA€JØŒE�!�Y×%Ñ%Ó&¨*Ñ4Ñ4€Dð
 	ŒE�!�Y×'Ñ'Ó(Ñ(€Dô  °¸Ô;€FØ�Z‰Z˜Ó€Fð �‚{Ü�‰Ð;¼XÀfÑ=MÔNØˆ	ô +0°«.Ö9 QŒE�!�A‘$—-‘-Õ Ò9Ð9ùÒ9s   ÈH?)r   NN)&Úloggingr�   Úenumr   Útypingr   Ú"torch.distributed._tools.ilp_utilsr   r   Ú&torch.distributed._tools.sac_estimatorr   Úpulpr   r	   r
   r   r   r   r   r   r   r   ÚImportErrorÚerrÚ	getLoggerro   rJ   ÚsetLevelÚINFOÚfloatÚintrE   ÚstrÚtupleÚdictrk   rn   rŒ   rt   rl   r*   ú<module>r�      s  ðÛ Û Ý Ý ç BÝ ;ð÷÷ ÷ ð$ 
ˆ×	Ñ	˜8Ó	$€ð ‡��—‘Ô ð Ø$(Ø&*ñv6Øðv6àðv6ð ðv6ð �t˜C‘yÑ!ð	v6ð
 ˜˜c™Ñ#ðv6ð ˆ4��U�
Ñ˜U CÐ'Ñ(óv6ôr�'ô ð
F:ØðF:Ø(-ðF:à	ˆ#�YôF:øðU ò Ù
ØLóàðûðús   ¤B- Â-C Â2	B;Â;C 