
    dafF                     &   d Z ddlZddlZddlZddlZddlZddlZddlZddlZddl	Z	ddl
Z
ddlZddlZddlmZ ddlmZ ddlmZ dZej&                  d        Z ej*                   eed      d	       G d
 dej.                               Z ej*                   eed      d	       G d de             Z ej*                   eed      d	       G d de             Z ej*                   eed      d	       G d de             Z ej*                   eed      d	       ej*                   eed      d       G d de                    Z ej*                   eed      d	       G d de             Z G d de      Zedk(  r ej@                          yy)a  
This test suite exercises some system calls subject to interruption with EINTR,
to check that it is actually handled transparently.
It is intended to be run by the main test suite within a child process, to
ensure there is no background thread running (so that signals are delivered to
the correct thread).
Signals are generated in-process using setitimer(ITIMER_REAL), which allows
sub-second periodicity (contrarily to signal()).
    N)support)	os_helper)socket_helperg{Gz?c              #   r   K   | 5  	 |  	 ddd       y#  | j                           xY w# 1 sw Y   yxY ww)zGContext manager killing the subprocess if a Python exception is raised.N)kill)procs    +/root/Python-3.12.4/Lib/test/_test_eintr.pykill_on_errorr
   "   sA      
 	J 	IIK s    7+	7(+47	setitimerzrequires setitimer()c                   J    e Zd ZdZdZdZdZd Zd Ze	d        Z
d Zd Zd	 Zy
)EINTRBaseTestz Base class for EINTR tests. g?g?c                 .    | xj                   dz  c_         y N   )signals)selfsignumframes      r	   
sighandlerzEINTRBaseTest.sighandler9   s        c                 6   d| _         t        j                  t        j                  | j                        | _        t        j
                  t        j                  | j                  | j                         t        j                  ddt        j                         y )Nr   iX  T)exitfile)r   signalSIGALRMr   orig_handlerr   ITIMER_REALsignal_delaysignal_periodfaulthandlerdump_traceback_latersys
__stderr__r   s    r	   setUpzEINTRBaseTest.setUp<   sf    "MM&..$//J++T->->++	-
 	))'/2~~	?r   c                  N    t        j                  t         j                  dd       y Nr   )r   r   r    r   r	   
stop_alarmzEINTRBaseTest.stop_alarmG   s    ++Q2r   c                     | j                          t        j                  t        j                  | j                         t	        j
                          y N)r)   r   r   r   r    cancel_dump_traceback_laterr$   s    r	   tearDownzEINTRBaseTest.tearDownK   s0    fnnd&7&78002r   c                 X    t         j                  df|z   }t        j                  |fi |S )Nz-c)r"   
executable
subprocessPopen)r   argskwcmd_argss       r	   r0   zEINTRBaseTest.subprocessP   s+    NND)D0/B//r   c                 J    | j                  || j                  t        z
         y r+   )assertGreaterEqual
sleep_time	CLOCK_RES)r   elapseds     r	   check_elapsed_timez EINTRBaseTest.check_elapsed_timeT   s    9)DEr   N)__name__
__module____qualname____doc__r   r   r7   r   r%   staticmethodr)   r-   r0   r:   r(   r   r	   r   r   -   sF    ' LM J	? 3 33
0Fr   r   c                       e Zd ZdZd Zd Zd Z ej                   e	e
d      d      d        Zd Zd	 Z ej                   e	e
d
      d      d        Zd Zd Zy)OSEINTRTestz  EINTR tests for the os module. c                 B    d| j                   z  }| j                  |      S )Nzimport time; time.sleep(%r))r7   r0   )r   codes     r	   new_sleep_processzOSEINTRTest.new_sleep_process\   s    ,t>t$$r   c                     d}t        |      D cg c]  }| j                          }}t        |      D ]	  } |         |D ]  }|j                           y c c}w )N   )rangerD   wait)r   	wait_funcnum_	processesr   s         r	   _test_wait_multiplezOSEINTRTest._test_wait_multiple`   s_    7<SzB!T++-B	Bs 	AK	  	DIIK		 Cs   Ac                 B    | j                  t        j                         y r+   )rM   osrH   r$   s    r	   	test_waitzOSEINTRTest.test_waiti   s      )r   wait3zrequires wait3()c                 (    | j                  d        y )Nc                  ,    t        j                  d      S r'   )rO   rQ   r(   r   r	   <lambda>z(OSEINTRTest.test_wait3.<locals>.<lambda>n   s    ! r   )rM   r$   s    r	   
test_wait3zOSEINTRTest.test_wait3l   s      !45r   c                 h    | j                         } ||j                         |j                          y r+   )rD   pidrH   )r   rI   r   s      r	   _test_wait_singlezOSEINTRTest._test_wait_singlep   s%    %%'$((		r   c                 (    | j                  d        y )Nc                 .    t        j                  | d      S r'   )rO   waitpidrW   s    r	   rT   z*OSEINTRTest.test_waitpid.<locals>.<lambda>w   s    2::c1+= r   rX   r$   s    r	   test_waitpidzOSEINTRTest.test_waitpidv   s    =>r   wait4zrequires wait4()c                 (    | j                  d        y )Nc                 .    t        j                  | d      S r'   )rO   r_   r\   s    r	   rT   z(OSEINTRTest.test_wait4.<locals>.<lambda>{   s    288C+; r   r]   r$   s    r	   
test_wait4zOSEINTRTest.test_wait4y   s    ;<r   c                 "   t        j                         \  }}| j                  t         j                  |       g d}dj	                  dddd|z  d| j
                  z  ddd	d
df
      }| j                  |t        |      |g      }t        |      5  t        j                  |       |D ]1  }| j                  |t        j                  |t        |                   3 | j                  |j                         d       d d d        y # 1 sw Y   y xY w)N)s   hellos   worlds   spam
zimport os, sys, time zwr = int(sys.argv[1])
datas = %rsleep_time = %rzfor data in datas:z$    # let the parent block on read()    time.sleep(sleep_time)z    os.write(wr, data)pass_fdsr   )rO   pipe
addCleanupclosejoinr7   r0   strr
   assertEqualreadlenrH   )r   rdwrdatasrC   r   datas          r	   	test_readzOSEINTRTest.test_read}   s    B"%
 .yy"#5 / 2($
  tSWt<4  	-HHRL ?  rwwr3t9'=>?TYY[!,		- 	- 	-s   A,DDc                    t        j                         \  }}| j                  t         j                  |       dt        j
                  z  }dj                  dddd| j                  z  dt        j
                  z  ddd	d
ddddddddddf      }| j                  |t        |      |g      }t        |      5  t        j                  |       d}|t        |      k  r4|t        j                  |t        |      |d        z  }|t        |      k  r4| j                  |j                         d       d d d        y # 1 sw Y   y xY w)N   xrd   zimport io, os, sys, timere   zrd = int(sys.argv[1])rg   zdata = b"x" * %sdata_len = len(data)z!# let the parent block on write()time.sleep(sleep_time)zread_data = io.BytesIO()z+while len(read_data.getvalue()) < data_len:z%    chunk = os.read(rd, 2 * data_len)z    read_data.write(chunk)zvalue = read_data.getvalue()zif value != data:z0    raise Exception("read error: %s vs %s bytes"z-                    % (len(value), data_len))ri   r   )rO   rk   rl   rm   r   PIPE_MAX_SIZErn   r7   r0   ro   r
   rr   write
memoryviewrp   rH   )r   rs   rt   rv   rC   r   writtens          r	   
test_writezOSEINTRTest.test_write   s/   B"% g+++yy&#/!6!66"/$&93(*>;'
 , tSWt<4  	-HHRLGCI%288B
4(8(BCC CI%TYY[!,	- 	- 	-s   6AD9 D99EN)r;   r<   r=   r>   rD   rM   rP   unittest
skipUnlesshasattrrO   rU   rX   r^   rb   rw   r   r(   r   r	   rA   rA   X   s    *%* XW-/AB6 C6? XW-/AB= C=-:$-r   rA   c                   &   e Zd ZdZ ej
                   eed      d      d        Zd Z	 ej
                   eej                  d      d      d        Z
d	 Zd
 Zd Z ej
                   eej                  d      d      d        Zd Z ej"                  dd       ej
                   eed      d      d               Zd Z ej*                  ej.                  dk(  d      d        Zd Z ej*                  ej.                  dk(  d      d        Zy)SocketEINTRTestz$ EINTR tests for the socket module. 
socketpairzneeds socketpair()c                 x   t        j                         \  }}| j                  |j                         g d}dj	                  ddddt        |j                        z  dt        |j                        z  d|z  d	| j                  z  dd
dddddddf      }|j                         }| j                  |t        |      |g      }t        |      5  |j                          |D ]$  }| j                  | ||t        |                   & | j                  |j                         d       d d d        y # 1 sw Y   y xY w)N)ry      y   zrd   import os, socket, sys, timere   fd = int(sys.argv[1])family = %ssock_type = %srf   rg   z)wr = socket.fromfd(fd, family, sock_type)os.close(fd)zwith wr:z    for data in datas:z(        # let the parent block on recv()z        time.sleep(sleep_time)z        wr.sendall(data)ri   r   )socketr   rl   rm   rn   intfamilytyper7   filenor0   ro   r
   rp   rr   rH   )	r   	recv_funcrs   rt   ru   rC   fdr   rv   s	            r	   
_test_recvzSocketEINTRTest._test_recv   s%   ""$B! #yy*#C		N*s277|+5 /7$6,&!
 & YY[tSWt<4  	-HHJ A  ySY'?@ATYY[!,		- 	- 	-s   AD00D9c                 V    | j                  t        j                  j                         y r+   )r   r   recvr$   s    r	   	test_recvzSocketEINTRTest.test_recv       **+r   recvmsgzneeds recvmsg()c                 (    | j                  d        y )Nc                 *    | j                  |      d   S r'   )r   sockrv   s     r	   rT   z.SocketEINTRTest.test_recvmsg.<locals>.<lambda>   s    4<<+=a+@ r   )r   r$   s    r	   test_recvmsgzSocketEINTRTest.test_recvmsg   s    @Ar   c                    t        j                         \  }}| j                  |j                         dt        j
                  dz  z  }dj                  ddddt        |j                        z  dt        |j                        z  d	| j                  z  d
t        j
                  dz  z  dddddddddddddddddf      }|j                         }| j                  |t        |      |g      }t        |      5  |j                          d}|t        |      k  r6 ||t!        |      |d        }	||	t        |      n|	z  }|t        |      k  r6| j#                  |j%                         d       d d d        y # 1 sw Y   y xY w)Ns   xyzrF   rd   r   re   r   r   r   rg   zdata = b"xyz" * %srz   z)rd = socket.fromfd(fd, family, sock_type)r   zwith rd:z$    # let the parent block on send()rh   z'    received_data = bytearray(data_len)z	    n = 0z    while n < data_len:z8        n += rd.recv_into(memoryview(received_data)[n:])zif received_data != data:z0    raise Exception("recv error: %s vs %s bytes"z5                    % (len(received_data), data_len))ri   r   )r   r   rl   rm   r   SOCK_MAX_SIZErn   r   r   r   r7   r   r0   ro   r
   rr   r~   rp   rH   )
r   	send_funcrs   rt   rv   rC   r   r   r   sents
             r	   
_test_sendzSocketEINTRTest._test_send   sy   ""$B! ..!34yy*#C		N*s277|+/ G$9$9Q$>?"72(5%F'>C1
 6 YY[tSWt<4  	-HHJGCI% Z%5gh%?@3t9$> CI% TYY[!,	- 	- 	-s   8AE8 E88Fc                 V    | j                  t        j                  j                         y r+   )r   r   sendr$   s    r	   	test_sendzSocketEINTRTest.test_send  r   r   c                 V    | j                  t        j                  j                         y r+   )r   r   sendallr$   s    r	   test_sendallzSocketEINTRTest.test_sendall!  s    --.r   sendmsgzneeds sendmsg()c                 (    | j                  d        y )Nc                 &    | j                  |g      S r+   )r   r   s     r	   rT   z.SocketEINTRTest.test_sendmsg.<locals>.<lambda>&  s    4<<+? r   )r   r$   s    r	   test_sendmsgzSocketEINTRTest.test_sendmsg$  s    ?@r   c                 
   t        j                  t        j                  df      }| j	                  |j
                         |j                         d   }dj                  dddt        j                  z  d|z  d| j                  z  dd	d
ddf
      }| j                  |      }t        |      5  |j                         \  }}|j                          | j                  |j                         d       d d d        y # 1 sw Y   y xY w)Nr   r   rd   zimport socket, timere   z	host = %rz	port = %srg   z# let parent block on accept()r{   z,with socket.create_connection((host, port)):rh   )r   create_serverr   HOSTrl   rm   getsocknamern   r7   r0   r
   acceptrp   rH   )r   r   portrC   r   client_sockrK   s          r	   test_acceptzSocketEINTRTest.test_accept(  s    ##]%7%7$;<

#!!$yy!-,,,$/,$:(
  t$4  	-![[]NKTYY[!,	- 	- 	-s   ,AC99D
   rF   mkfifozneeds mkfifo()c                    t         j                  }t        j                  |       	 t        j                  |       | j                  t         j                  |       dj                  ddd|z  d| j                  z  dddd|f	      }| j                  |      }t        |      5   ||       | j                  |j                         d	       d d d        y # t
        $ r}| j                  d|z         Y d }~d }~ww xY w# 1 sw Y   y xY w)
Nzos.mkfifo(): %srd   import os, timere   z	path = %arg   z# let the parent blockr{   r   )r   TESTFNunlinkrO   r   PermissionErrorskipTestrl   rn   r7   r0   r
   rp   rH   )r   do_open_close_readerdo_open_close_writerfilenameerC   r   s          r	   
_test_openzSocketEINTRTest._test_openD  s     ## 	"	1IIh 		(((3yy("/$$ 

 
 t$4  	- *TYY[!,	- 	-#  	1MM+a/00	1"	- 	-s#   C ")C>	C;C66C;>Dc                 <    t        |d      }|j                          y )Nw)openrm   )r   pathfps      r	   python_openzSocketEINTRTest.python_openc  s    $_

r   darwinz+hangs under macOS; see bpo-25234, bpo-35363c                 <    | j                  d| j                         y )Nzfp = open(path, 'r')
fp.close())r   r   r$   s    r	   	test_openzSocketEINTRTest.test_openg  s     	:((	*r   c                 v    t        j                  |t         j                        }t        j                  |       y r+   )rO   r   O_WRONLYrm   )r   r   r   s      r	   os_openzSocketEINTRTest.os_openm  s!    WWT2;;'
r   c                 <    | j                  d| j                         y )Nz,fd = os.open(path, os.O_RDONLY)
os.close(fd))r   r   r$   s    r	   test_os_openzSocketEINTRTest.test_os_openq  s     	G	&r   N)r;   r<   r=   r>   r   r   r   r   r   r   r   r   r   r   r   r   r   requires_freebsd_versionrO   r   r   skipIfr"   platformr   r   r   r(   r   r	   r   r      sY   .X68LM!- N!-F, X	:<MNB OB,-\,/ X	:<MNA OA-8 &W%%b!,XX.0@A- B --: X__S\\X-BD*D* X__S\\X-BD&D&r   r   c                       e Zd ZdZd Zy)TimeEINTRTestz" EINTR tests for the time module. c                     t        j                         }t        j                  | j                         | j	                          t        j                         |z
  }| j                  |       y r+   )time	monotonicsleepr7   r)   r:   r   t0dts      r	   
test_sleepzTimeEINTRTest.test_sleep|  sG    ^^

4??#^^"#r   N)r;   r<   r=   r>   r   r(   r   r	   r   r   x  s
    ,$r   r   pthread_sigmaskzneed signal.pthread_sigmask()c                       e Zd ZdZd Z ej                   eed      d      d        Z	 ej                   eed      d      d        Z
y)	SignalEINTRTestz$ EINTR tests for the signal module. c                    t         j                  }t        j                         }t        j                   |d       }| j	                  t         j                   ||       dj                  ddt        j                         z  dt        |      z  d| j                  z  ddf      }t        j                  t         j                  |g      }| j	                  t         j                  t         j                  |g       | j                  |      }t        |      5   ||       d d d        | j                  |j                         d	       y # 1 sw Y   *xY w)
Nc                       y r+   r(   )r2   s    r	   rT   z/SignalEINTRTest.check_sigwait.<locals>.<lambda>  s    r   rd   r   zpid = %szsignum = %srg   r{   zos.kill(pid, signum)r   )r   SIGUSR1rO   getpidrl   rn   r   r7   r   	SIG_BLOCKSIG_UNBLOCKr0   r
   rp   rH   )r   rI   r   rW   old_handlerrC   old_maskr   s           r	   check_sigwaitzSignalEINTRTest.check_sigwait  s   iikmmF,>?v{;yy$CK'/$"
  ))&*:*:VHE..0B0BVHMt$4  	f	 	a(	 	s   	EEsigwaitinfozneed signal.sigwaitinfo()c                 ,    d }| j                  |       y )Nc                 0    t        j                  | g       y r+   )r   r   r   s    r	   rI   z3SignalEINTRTest.test_sigwaitinfo.<locals>.wait_func  s    x(r   r   r   rI   s     r	   test_sigwaitinfoz SignalEINTRTest.test_sigwaitinfo  s    	) 	9%r   sigtimedwaitc                 ,    d }| j                  |       y )Nc                 2    t        j                  | gd       y )Ng      ^@)r   r   r   s    r	   rI   z4SignalEINTRTest.test_sigtimedwait.<locals>.wait_func  s    %0r   r   r   s     r	   test_sigtimedwaitz!SignalEINTRTest.test_sigtimedwait  s    	1 	9%r   N)r;   r<   r=   r>   r   r   r   r   r   r   r   r(   r   r	   r   r     sf     /)2 X746&6& X846&6&r   r   c                   \   e Zd ZdZd Z ej                  ej                  dk(  d       ej                   e
ed      d      d               Z ej                   e
ed      d	      d
        Z ej                   e
ed      d      d        Z ej                   e
ed      d      d        Zy)SelectEINTRTestz$ EINTR tests for the select module. c                     t        j                         }t        j                  g g g | j                         t        j                         |z
  }| j	                          | j                  |       y r+   )r   r   selectr7   r)   r:   r   s      r	   test_selectzSelectEINTRTest.test_select  sM    ^^b"b$//2^^"#r   r   z(poll may fail on macOS; see issue #28087pollzneed select.pollc                     t        j                         }t        j                         }|j                  | j                  dz         t        j                         |z
  }| j                          | j                  |       y Ng     @@)r   r   r   r   r7   r)   r:   r   pollerr   r   s       r	   	test_pollzSelectEINTRTest.test_poll  sY     ^^DOOc)*^^"#r   epollzneed select.epollc                 0   t        j                         }| j                  |j                         t	        j
                         }|j                  | j                         t	        j
                         |z
  }| j                          | j                  |       y r+   )
r   r  rl   rm   r   r   r   r7   r)   r:   r   s       r	   
test_epollzSelectEINTRTest.test_epoll  sb    %^^DOO$^^"#r   kqueuezneed select.kqueuec                 4   t        j                         }| j                  |j                         t	        j
                         }|j                  d d| j                         t	        j
                         |z
  }| j                          | j                  |       y r   )
r   r  rl   rm   r   r   controlr7   r)   r:   )r   r  r   r   s       r	   test_kqueuezSelectEINTRTest.test_kqueue  sf    %^^tQ0^^"#r   devpollzneed select.devpollc                 6   t        j                         }| j                  |j                         t	        j
                         }|j                  | j                  dz         t	        j
                         |z
  }| j                          | j                  |       y r   )
r   r	  rl   rm   r   r   r   r7   r)   r:   r   s       r	   test_devpollzSelectEINTRTest.test_devpoll  sh    !%^^DOOc)*^^"#r   N)r;   r<   r=   r>   r   r   r   r"   r   r   r   r   r  r  r  r  r(   r   r	   r   r     s    .$ X__S\\X-?AX02DE$ FA$ X13FG$ H$ X24HI$ J$ X35JK$ L$r   r   c                   n    e Zd Zd Z ej
                   ej                         dk(  d      d        Zd Z	y)FNTLEINTRTestc                    | j                  t        j                  t        j                         dj	                  ddt        j                  z  d|z  d| j
                  z  f      }t        j                         }| j                  |      }t        |      5  t        t        j                  d      5 }t        j                         }t        j                  t        j                  d      D ]B  }	  ||t        j                  t        j                   z          ||t        j"                         D t        j                         |z
  }t'        d	|z        # t$        $ r Y  nw xY w ||t        j                         t        j                         |z
  }| j)                          | j+                  |       d d d        n# 1 sw Y   nxY w|j-                          d d d        y # 1 sw Y   y xY w)
Nrd   zimport fcntl, timezwith open('%s', 'wb') as f:z   fcntl.%s(f, fcntl.LOCK_EX)z   time.sleep(%s)wbF)errorz failed to sync child in %.1f sec)rl   r   r   r   rn   r7   r   r   r0   r
   r   r   sleeping_retryLONG_TIMEOUTfcntlLOCK_EXLOCK_NBLOCK_UNBlockingIOError	Exceptionr)   r:   rH   )	r   	lock_func	lock_namerC   
start_timer   frK   r   s	            r	   _lockzFNTLEINTRTest._lock  s   	(()*:*:;yy )I,<,<<+i7$//1	3 4
 ^^%
t$4  	i&&- ,!^^-
 //0D0DER MA!!U]]U]]%BC!!U]]3M )J6B#$F$KLL	 +  !U]]+^^%
2!''+', , ,( IIK+	 	 	sI   G!0=F<.?E-'F<	E!	F< E!	!AF<3	G!<G	G!!G*AIXzAIX returns PermissionErrorc                 D    | j                  t        j                  d       y )Nlockf)r  r  r   r$   s    r	   
test_lockfzFNTLEINTRTest.test_lockf  s    

5;;(r   c                 D    | j                  t        j                  d       y )Nflock)r  r  r#  r$   s    r	   
test_flockzFNTLEINTRTest.test_flock  s    

5;;(r   N)
r;   r<   r=   r  r   r   r   systemr!  r$  r(   r   r	   r  r    s>    D X___X__&%/1NO) P))r   r  __main__)!r>   
contextlibr    r  rO   r   r   r   r   r0   r"   r   r   testr   test.supportr   r   r8   contextmanagerr
   r   r   TestCaser   rA   r   r   r   r   r  r;   mainr(   r   r	   <module>r-     s      	      
    " &
 	   WV[13IJ'FH%% 'F K'FT WV[13IJe-- e- Ke-P WV[13IJs&m s& Ks&l WV[13IJ$M $ K$ WV[13IJ WV%6746*&m *&6 K
*&Z WV[13IJ5$m 5$ K5$p()M ()V zHMMO r   