h]"dZddlmZddlZddlZddlZddlZddlZddlZddl Z ddl m Z eddZ ej eZGddZGd d ZdS) u  This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program.  If not, see . Copyright © 2019 Cloud Linux Software Inc. This software is also available under ImunifyAV commercial license, see ) namedtupleN)sysctlEvent)pathflagscookienamewdceZdZdZdZdZdZdZdZdZ dZ d Z d Z d Z d Zd ZdZdZdZdZdZdZdZdZdZdejdkrdndZejedZe j!dZ"e#dZ$e#dZ%e#d Z&e#d!Z'e#d"Z(e#d#Z)d$S)%InotifyzE Tiny wrapper for inotify api. See `man inotify` for details  @iii i@iiiii i@lzlibc.{}Darwinzso.6dylibT) use_errnoiIIIcttj||}|dkr5tj}t |t j||S)a Wrapper to all calls to C functions. Raises OSError with appropriate errno as argument in case of error return value. :param method: method to call :param args: method args :return: called function return value in case of success )getattrr _libcctypes get_errnoOSErrorosstrerror)methodargsreterrnos T/opt/imunify360/venv/lib/python3.11/site-packages/imav/malwarelib/subsys/ainotify.py_callz Inotify._callIsR-ggmV,,d3 "99$&&E%U!3!344 4 c6tdS)z Initialize an inotify instance. See `man inotify_init` for details :return: a file descriptor of new inotify instance inotify_initr r)r*r(initz Inotify.initXs}}^,,,r*c<td|||S)a Add a watch to an initialized inotify instance. This method is idempotent. If called twice with the same :fd: and :path: and different mask, will change watch flags of current watch. See `man inotify_add_watch` for details :param fd: file descriptor returned by `init()` :param path: path to file or directory to watch :param mask: bitmask of events to monitor :return: file descriptor of watch inotify_add_watchr-)fdrmasks r( add_watchzInotify.add_watchas}}0"dDAAAr*c:td||S)z Remove existing watch from inotify instance. :param fd: file descriptor of inotify instance :param wd: watch file descriptor, returned by `add_watch()` :return: zero inotify_rm_watchr-)r2r s r(rm_watchzInotify.rm_watchos}}/R888r*c@tj|S)z Unpacks prefix of event struct. See `man inotify` for details :param data: struct bytestring :return: tuple of (wd, flag, cookie, length) )r event_prefixunpackdatas r( unpack_prefixzInotify.unpack_prefixys#**4000r*c~tjdt|z|ddS)z Unpack name field of inotify event struct See `man inotify` for details :param data: struct bytestring :return: name string z%dsr)structr:lenrstripr;s r( unpack_namezInotify.unpack_names4}USYY.55a8??HHHr*N)*__name__ __module__ __qualname____doc__ACCESSMODIFYATTRIB CLOSE_WRITE CLOSE_NOWRITEOPEN MOVED_FROMMOVED_TOCREATEDELETE DELETE_SELF MOVE_SELFUNMOUNT Q_OVERFLOWIGNOREDONLYDIR DONT_FOLLOW EXCL_UNLINKMASK_ADDISDIRONESHOTformatplatformsystem_nrCDLLrr@Structr9 staticmethodr)r/r4r7r=rCr.r*r(r r 'sF F FKM DJH F FKIGJGGKKH EG   OHO$5$5$A$A&&w O OB FKd + + +E 6=((L  \ --\- B B\ B99\911\1II\IIIr*r cZeZdZdZdZdZdZdZddZdZ d Z d Z d Z d Z d ZdZdZdS)Watcherz1 Asynchronous watcher for inotify events rg?zfs.inotify.max_user_watchesNc||_t|_t j|_|p |jj|_|j |j|j | dSN) _loopr r/_fdasyncioQueue_queueput _callback add_reader_read _reset_state)selfloop coro_callbacks r(__init__zWatcher.__init__si <<>>moo &9$+/ dh 333 r*c0i|_i|_d|_dS)Nr*)paths descriptorsbufrss r(rrzWatcher._reset_states r*cF|xjtj|j|jz c_t jj}t|j|krIt |jd|\}}}}||z}t |j||}|j|d|_||j vr|j |}|t j zr1td||||t jzrtdt%|||||} |j|| t|j|kGdSdS)Nz(Got IGNORED event for %s, cleaning watchzInotify queue overflow)rzr"readrj _CHUNK_SIZEr r9sizerAr=rCrxrVloggerwarning_cleanup_watchrUerrorrri create_taskro) rs struct_sizer rrlength struct_endr revs r(rqz Watcher._reads BGDHd&6777*/ $(mm{**(/(=(=+&)) %Bvv%v-J&&tx J0F'GHHDx ,DH##:b>Dw& >##D)))w))  5666tUFD"55B J " "4>>"#5#5 6 6 6/$(mm{******r*ctj|j}|t||jzz}t d|j|tj|j|dS)NzRaising %s to %s)rr}_MAX_USER_WATCHESint_WATCHERS_RAISE_COEFFrinfowrite)rscurrent_max_watchesnew_max_watcherss r(_raise_user_watcheszWatcher._raise_user_watchessx$k$*@AA. $"< <2 2     68H     T+-=>>>>>r*c|j|j tj|j|d|_dS#|d|_wxYw)za Close watcher. Close inotify fd, remove reader and reset state :return: N)ri remove_readerrjr"closerrr{s r(rz Watcher.closest   ***  HTX         DHHH      DHOOOOs AA4ct|ts Jdtd|d} t|j||}||j|<||j|<dS#t$rz}||j krN|j tj kr9| |dz }td|Yd}~td|d}~wwxYw) z Add file to watch :param path: file or directory to watch :param mask: events mask for this watch zPath must be bytesz Watching %rrTr z-Inotify: not enough watches (%r), retrying...Nz Inotify failed while watching %r) isinstancebytesrrr r4rjrxryr!_MAX_WATCH_RETRIESr'ENOSPCrrr)rsrr3retriesr es r(watchz Watcher.watchs $&&<<(<<<& M4(((  &&txt<<!% 2)+ &   d5555<//,,...qLGNNGHHHH ?FFF s5A66 C:AC5C55C:cz|j|d}||j|ddSdSrh)rypoprx)rsr descriptors r(rzWatcher._cleanup_watchsD%))$55  ! JNN:t , , , , , " !r*c||jvrdStd| t|j|j|||dS#||wxYw)zq Remove file or directory from watch :param path: file or directory to remove watch from NzStop watching %r)ryrrr r7rjr)rsrs r(unwatchzWatcher.unwatchs t' ' ' F &--- &   TXt'7'= > > >    % % % % %D   % % % %s +A**Bc~K|jd{V}td||S)zF Get watch event :return: `Event` named tuple NzInotify event: %s)rmgetrdebug)rsevents r( get_eventzWatcher.get_eventsE koo'''''''' (%000 r*rh)rDrErFrGr~rrrrvrrrqrrrrrrr.r*r(reresK5 777:???   :--- & & &r*re)rG collectionsrrkrr'loggingr"r@r^defence360agent.subsysrr getLoggerrDrr rer.r*r(rs*#"""""  )))))) 7EFF  8 $ $dIdIdIdIdIdIdIdIN@@@@@@@@@@r*