2323
2424from  scapy .error  import  Scapy_Exception 
2525from  scapy .packet  import  Packet 
26- from  scapy .contrib .coap  import  CoAP , coap_options , coap_codes 
26+ from  scapy .contrib .coap  import  CoAP , coap_options , coap_codes , EMPTY_MESSAGE , GET , \
27+     POST , PUT , DELETE , COAP_REQ_CODES , CONTENT_205 , NOT_FOUND_404 , NOT_ALLOWED_405 , \
28+     CF_TEXT_PLAIN , CF_APP_LINK_FORMAT , PAYMARK , URI_PATH , CONTENT_FORMAT , CON , NON , ACK 
2729from  scapy .contrib .isotp .isotp_soft_socket  import  TimeoutScheduler 
2830from  scapy .data  import  MTU 
2931from  scapy .utils  import  EDecimal 
3032from  scapy .automaton  import  ObjectPipe , select_objects 
3133
3234from  scapy .supersocket  import  SuperSocket , SimpleSocket 
3335
34- """ 
35- CoAP message request codes (RFC 7252 @ section-5.8.1) 
36- """ 
37- EMPTY_MESSAGE  =  0 
38- GET  =  1 
39- POST  =  2 
40- PUT  =  3 
41- DELETE  =  4 
42- COAP_REQ_CODES  =  [GET , POST , PUT , DELETE ]
43- """ 
44- CoAP message response codes (RFC 7252 @ section-12.1.2) 
45- Also, from scapy.contrib.coap.coap_codes 
46- """ 
47- EMPTY_ACK  =  EMPTY_MESSAGE 
48- CONTENT_205  =  69 
49- NOT_FOUND_404  =  132 
50- NOT_ALLOWED_405  =  133 
51- NOT_IMPLEMENTED_501  =  161 
52- """ 
53- CoAP content type (RFC 7252 @ section-12.3) 
54- """ 
55- CF_TEXT_PLAIN  =  b"\x00 " 
56- CF_APP_LINK_FORMAT  =  b"\x28 " 
57- CF_APP_XML  =  b"\x29 " 
58- CF_APP_OCTET_STREAM  =  b"\x2A " 
59- CF_APP_EXI  =  b"\x2F " 
60- CF_APP_JSON  =  b"\x32 " 
61- """ 
62- CoAP options (RFC 7252 @ section-5.10) 
63- """ 
64- PAYMARK  =  b"\xff " 
65- URI_PATH  =  11 
66- CONTENT_FORMAT  =  12 
67- """ 
68- CoAP message type 
69- """ 
70- CON  =  0 
71- NON  =  1 
72- ACK  =  2 
73- RST  =  3 
74- 
7536log_coap_sock  =  logging .getLogger ("scapy.contrib.coap_socket" )
7637
7738
@@ -85,7 +46,7 @@ class CoAPSocket(SuperSocket):
8546    >>> with CoAPSocket("127.0.0.1", 1234) as coap_client: 
8647    >>>     req = CoAPSocket.make_coap_req_packet( 
8748    >>>                 method=GET, uri="endpoint-uri", payload=b"") 
88-     >>>     coap_client.send("127.0.0 .1", 5683,  req) 
49+     >>>     coap_client.send(IP(dst="192.168.1 .1") / UDP(dport=1234) /  req) 
8950    >>>     # Careful, this will block until the coap_client receives something 
9051    >>>     res = coap_client.recv() 
9152
@@ -172,12 +133,24 @@ def recv(self, x=MTU, **kwargs):
172133    def  close (self ):
173134        # type: () -> None 
174135        if  not  self .closed :
175-             self .impl .close ()
176136            self .closed  =  True 
137+             self .impl .close ()
177138
178-     def  send (self , ip , port , x ):
179-         # type: (str, int, CoAP) -> None 
180-         self .impl .send (ip , port , x )
139+     def  send (self , x ):
140+         # type: (Packet) -> int 
141+         """ 
142+         Send the packet using this socket. 
143+         Should be a CoAP packet with IP and UDP data. 
144+ 
145+         Example: 
146+         >>> IP(dst="192.168.1.1") / UDP(dport=1234) / CoAP() 
147+         >>> IP(dst="192.168.1.1") / UDP(dport=1234) / CoAPSocket.make_coap_req_packet() 
148+ 
149+         :param x: Concatenated packet with IP / UDP / CoAP 
150+         :return: The length of x, which is the amount of bytes sent 
151+         """ 
152+         self .impl .send (x .dst , x .dport , x [CoAP ])
153+         return  len (x )
181154
182155    @staticmethod  
183156    def  make_coap_req_packet (method = GET , uri = "" , options = None , payload = b"" ):
@@ -630,7 +603,7 @@ def _on_pkt_recv(self, pkt, sa_ll):
630603            else :
631604                self ._handle_rcv_request (pkt , sa_ll )
632605        else :
633-             # Response, check pending requests 
606+             # Response, check pending requests and process internally  
634607            self ._handle_request_response (pkt , sa_ll )
635608
636609    def  _post (self ):
@@ -805,7 +778,6 @@ def _handle_request_response(self, pkt, sa_ll):
805778                                index [0 ], index [1 ],
806779                                coap_codes [pkt .code ])
807780            del  self .pending_requests [index ]
808-             # Piggybacked message, give it to the user 
809781            self .rx_queue .send ((pkt .build (), pkt .time ))
810782        elif  pkt .type  ==  ACK  and  pkt .code  ==  EMPTY_MESSAGE :
811783            log_coap_sock .debug (
@@ -824,11 +796,9 @@ def _handle_request_response(self, pkt, sa_ll):
824796            response  =  CoAPSocketImpl .empty_ack_params ()
825797            response ["msg_id" ] =  pkt .msg_id 
826798            self ._sock_send (sa_ll , CoAP (** response ))
827- 
828-             # Give the packet to the user 
829799            self .rx_queue .send ((pkt .build (), pkt .time ))
830800        else :
831-             log_coap_sock .info ("Not handled message, giving to user : " 
801+             log_coap_sock .info ("Not handled message: " 
832802                               "type=%s; code=%s;" ,
833803                               pkt .type , coap_codes [pkt .code ])
834804            self .rx_queue .send ((pkt .build (), pkt .time ))
0 commit comments