o Fa|@sddlZddlZddlZddlmZddlmZGdddZGdddeZGdd d eZ Gd d d eZ Gd d d eZ GdddeZ GdddeZ GdddeZGdddeZGdddZGdddZdS)NUFWError)debugc@s(eZdZdZddZddZddZdS) UFWCommandz"Generic class for parser commands.cCs,||_g|_||jvr|j|||_dSN)commandtypesappendtype)selfr rr ,/usr/lib/python3/dist-packages/ufw/parser.py__init__.s    zUFWCommand.__init__cCs&t|dkr tt|d}|S)Nr)len ValueErrorUFWParserResponselowerr argvrr r r parse5s zUFWCommand.parsecCstd)Nz!UFWCommand.help: need to overrider)r argsr r r help=szUFWCommand.helpN)__name__ __module__ __qualname____doc__rrrr r r r r,s  rc@s0eZdZdZddZddZddZeeZdS) UFWCommandRulez#Class for parsing ufw rule commandscCd}t|||dS)Nrulerrr rr r r r rCzUFWCommandRule.__init__c Cs d}d}d}d}d}d}d}d} d} d} t|dkr)|ddkr)||dt|dkr|ddkrkt|dkrkd} ||dd} zt|d} Wn ty]|d}Ynw| durjtd | } | Sn;|dd krt|d kr|t|d} | d ks| d krtd| }t||d=|d=n |ddkrd} |d=|d}|dkr|dkr|dkr|dkrtt|}|dkrtd}|dkr|ddks|ddkr|d}|dkr|ddkr|ddks|ddkr|d}|d=t|}d}|dkr[| ddks&| ddkr[td}|ddkr@|ddkr@t||dksN|ddkrRt||d=t|}d}d}|rz|dkrz|ddksw|ddkrzd}n|dkr|ddks|ddkrd}|dkr||} ||=t|}d|vrtd}t|d|vrtd}t|d}d|vr| d}|t|dkrtd }t|||d}d!|vrtd"}t|||d=||=t|}|dks|d#krt|}| dkr|d$| 7}t j j |dd|t j|d%}| r+| |_n| dkrAz|| Wn ty@w|dkrt j|drsz t j|dWntyrd&}|d|_||dd'Ynw|jdkrz t j|d\}}Wnty}zt|d}~wwtd(|sd)|vsd*|vrtd+}t||}z||||d'd&}Wnctytd,}t|wnQ|dddkrtd-}t|d.|vrd/|vrd|vrd|vrtd0}t|gd1}| d/dksN| d.dksN| d2dksN| d3dksN| ddksN| ddksN| d4dksN| d4dkrV| d2dkrVtd5}t|d}d}|D]}|ddkry|||vrytd6||}t||d2kr|d|krz |||dWn[tywtd7}t||dks|dkr|d|krz"|dkr|d||dn|dkr|d||dWntywtd8|}t||d.kr1|d|kr)z&||d}|dkr d9}d}n t j|d:rd;}nd<}||Wn ty%wd=}ntd>}t||d/krx|d|krpz&||d}|dkrPd9}d}n t j|d:r[d;}nd<}||Wn tylwd'}n}td?}t||d3ks|d4kr|d|kr|dkrtd@|}t|||d}|d4kr|d=kr||_n'||_n#td(|sd)|vsd*|vrtd+}t||d=kr|}n|}z|||WntywtdA}t||d7}q\|dkr|dkrd&}n&|dkr|dkr||krtdB}t||dkr|}n|dkr&|}|dks0|dkrd}|dkrPzt j|}WntyOtdC}t|w|dkr|dks_|dkrxzt j|}WnDtywtdC}t|wzt j|}WntytdC}t|w|dks||kr|}n|dkrntdD}t||jdkr||n|dkr|j|krtdE|j}t||r|jt jj vr|d&krt!dF|jd<}|"|t|} |j#| j$dG<|| j$d<|| j$dH<| S)INanyFrr deleterTz delete-%dinsert0z-1z#Cannot insert rule at position '%s'prependallowdenyrejectlimitinoutonzInvalid interface clauselogzlog-allzOption 'log' not allowed herez!Option 'log-all' not allowed herecommentz*Option 'comment' missing required argument'zComment may not contain "'" _) directionr6bothdstz^\d([0-9,:]*\d+)*$,:zPort ranges must be numericzBad portzWrong number of argumentsfromtozNeed 'to' or 'from' clause)protor?r@portappr1r2rArBrCzImproper rule syntaxzInvalid token '%s'zInvalid 'proto' clausezInvalid '%s' clause 0.0.0.0/06v6v4srczInvalid 'from' clausezInvalid 'to' clausezNeed 'from' or 'to' with '%s'zInvalid 'port' clausez%Mixed IP versions for 'from' and 'to'zCould not find protocolzProtocol mismatch (from/to)z,Protocol mismatch with specified protocol %sz*Adjusting iptype to 'v4' for protocol '%s'r iptype)%rrremoveint Exceptionrrr9rcountindexufwcommonUFWRuleutil hex_encode set_position applicationsvalid_profile_nameget_services_protodappset_portparse_port_protorematch set_protocol set_interface valid_addressset_srcset_dstsappprotocolipv4_only_protocolsrverifyr data) r ractionr r from_typeto_type from_service to_service insert_poslogtyperJrule_numrerr_msgnargsrule_direction has_interfacelog_idxr6 comment_idx rule_actionrBrAekeysilocargfaddrsaddrtmpr r r rGsj      * *$"                                                  zUFWCommandRule.parsecCs|j}|jdks |jdkr|jdks|jdkr|jdkr|jdkr|jdkr|jdkr|jdkr|jdkr<|d|j7}|j dkrH|d|j 7}|j dkrbd|j vrZ|d|j 7}n|d|j 7}n|d|j7}|j dkru|d |j 7}|j dkr|d | 7}|S|jdkr|d |j7}|jdkr|d |j7}n |jdkr|d|j7}|j dkr|d|j 7}d D]_}|dkr|j}|j}|j}d}n |j}|j}|j }d}|dks|dkrd}|dks|dks|dkr|d||f7}|dkr d|vr|d|7}q|d|7}q|dkr|d|7}qd|vr1d|vr1|jdkr1|jdkr1|d7}|j dkrJ|j dkrJ|jdkrJ|d|j 7}|j dkrX|d | 7}|S)zGet command string for rulerDz::/0r%r$r2z %s z '%s'z/%sz comment '%s'z in on %sz out on %s)rHr<rHr?r@z %s %sz app '%s'z app %sz port %sz to z from z to anyz proto %s)rgr<rHsportrb interface_in interface_outdportr:rmrXrcr6 get_comment)rresrxryrBrCdirr r r get_commandsv           2        $ zUFWCommandRule.get_commandN)rrrrrrr staticmethodr r r r rAs Mrc@ eZdZdZddZddZdS)UFWCommandRouteRulez)Class for parsing ufw route rule commandscCst||d|_dS)Nroute)rrr )r rr r r rs  zUFWCommandRouteRule.__init__c Csh|ddksJd|vr3|d}d}t||kr3zt||dtd}t|ty2Ynwd}d}d}d|}d|vrrd |vrrd }|d |d krTd }|||d }|d|||||d d}ntd|std|sd|vsd|vrtd}t||}d|d<t ||}d|j vrd|j d_ |r|r|j d |||S)Nrrr&r$rz9'route delete NUM' unsupported. Use 'delete NUM' instead.r~z in on z out on r2r1r0r4z (in|out) on z app (in|out) z in z out z'Invalid interface clause for route ruler T)rNrrKr9rrjoinr[searchrrrfforwardr^) r ridxro rule_argv interfacestripsrr r r rsH     *     zUFWCommandRouteRule.parseNrrrrrrr r r r r rc@r) UFWCommandAppz*Class for parsing ufw application commandscCr)NrCr!r"r r r rZr#zUFWCommandApp.__init__cCsJd}d}d}|ddkrt|d=t|}|d}|dks$|dkrO|dkr9|dd kr9d }|d t|}|d kr@tt|dd }|rO|d 7}|dkrZ|dkrZt|dkr|d kret|ddkrpd}n$|ddkr{d}n|ddkrd}n|ddkrd}ntt|}|j|jd<||jd<|S)zParse applications command.r$FrrCinfoupdater4rz --add-newTr0z[']z -with-newlistdefaultr, default-allowr- default-denyr.default-rejectskipz default-skipr name) rrrrJstrrrr rf)r rrrgaddnewrprr r r r^sH     zUFWCommandApp.parseNrr r r r rXrrc@r)UFWCommandBasicz$Class for parsing ufw basic commandscCr)Nbasicr!r"r r r rr#zUFWCommandBasic.__init__cCst|dkr tt||S)Nr)rrrr)r rr r r rs  zUFWCommandBasic.parseNrr r r r rrrc@r)UFWCommandDefaultz&Class for parsing ufw default commandscCr)Nrr!r"r r r rr#zUFWCommandDefault.__init__cCsJt|dkr td}d}t|dkrw|ddkrF|ddkrF|ddkrF|ddkrF|ddkrF|ddkrFt|dd rRd}n%|dd r^d}n|ddksn|ddkrqd}n|d}|d d krd }n|d dkrd}n|d dkrd}nt|d|7}t|S)Nr0r$incominginputroutedroutputoutgoingr1r2rr-rr,rr.rz-%s)rrr startswithr)r rrgr:r r r rs8     zUFWCommandDefault.parseNrr r r r rrrc@r)UFWCommandLoggingz&Class for parsing ufw logging commandscCr)Nloggingr!r"r r r rr#zUFWCommandLogging.__init__cCsd}t|dkr t|ddkrd}t|S|ddksA|ddksA|ddksA|dd ksA|dd krYd }|ddkrU|d |d7}t|St) Nr$r0roffz logging-offr3lowmediumhighfullz logging-onr9rrrrr rrgr r r rs  zUFWCommandLogging.parseNrr r r r rrrc@r)UFWCommandStatusz%Class for parsing ufw status commandscCr)Nstatusr!r"r r r rr#zUFWCommandStatus.__init__cCslt||}t|dkrd|_|St|dkr4|ddkr$d|_|S|ddkr1d|_|St|S)Nrrverbosezstatus-verbosenumberedzstatus-numbered)rrrrgrrrr r r rs   zUFWCommandStatus.parseNrr r r r rrrc@r)UFWCommandShowz#Class for parsing ufw show commandscCr)Nshowr!r"r r r rr#zUFWCommandShow.__init__cCsd}t|dkr t|ddkrd}t|S|ddkr'd}t|S|ddkr5d}t|S|dd krCd }t|S|dd krQd }t|S|dd kr_d}t|S|ddkrmd}t|S|ddkr{d}t|St)Nr$rrawzshow-rawz before-rulesz show-beforez user-rulesz show-userz after-rulesz show-afterz logging-rulesz show-loggingbuiltinsz show-builtins listeningzshow-listeningaddedz show-addedrrr r r rs8   zUFWCommandShow.parseNrr r r r rrrc@r)rzClass for ufw parser responsecCs ||_d|_d|_i|_dS)NF)rrgdryrunforcerf)r rgr r r rs  zUFWParserResponse.__init__cCsPd|j}t|j}||D] }|d||j|f7}q|d7}t|S)Nz action='%s'z,%s='%s' )rgrrfrwsortrepr)r rrwrxr r r __str__!s zUFWParserResponse.__str__N)rrrrrrr r r r rs rc@s0eZdZdZddZddZddZdd Zd S) UFWParserzClass for ufw parsercCs i|_dSr)commands)r r r r r.s zUFWParser.__init__cCsD|t|jvrt|t|j|vrt|S)z=Return command if it is allowed, otherwise raise an exception)rrrrwr)r r cmdr r r allowed_command1s zUFWParser.allowed_commandc Csrd}t|dkr|ddkrd}||dd}t|dkr:|ddks1|ddkr:d}||dd}d}|d}t|dkrk|t|jvrk|dt|j|vrk|}|d}n4|}t|jD]$}||j|vrt|j||trt|j||d d krqt|}nqt|dkrd }| ||}|j||}| |} || _ || _ | S) z(Parse command. Returns a UFWParserActionFrz --dry-runTz--forcez-fr$rr r ) rrrJrrrw isinstancergetattrrrrr) r rrrrr r}rxrgresponser r r parse_command;sB    zUFWParser.parse_commandcCsz|jdus |jdkrd|j}nd|j}|j|jvr!i|j|j<||j|jvr3td|}t|||j|j|<dS)z"Register a command with the parserNr$z%szCommand '%s' already exists)rr rr9r)r ckeyror r r register_commandis     zUFWParser.register_commandN)rrrrrrrrr r r r r,s  .r)r[ufw.utilrOufw.applications ufw.commonrrrrrrrrrrrrrr r r r s&$  YA; .