Internal ObjectPipe function.
(self, x)
| 1016 | self.PipeFileId = None |
| 1017 | |
| 1018 | def send(self, x): |
| 1019 | """ |
| 1020 | Internal ObjectPipe function. |
| 1021 | """ |
| 1022 | # Reminder: this class is an ObjectPipe, it's just a queue. |
| 1023 | |
| 1024 | # Detect if DCE/RPC is fragmented. Then we must use Read/Write |
| 1025 | is_frag = x.pfc_flags & 3 != 3 |
| 1026 | |
| 1027 | if self.use_ioctl and not is_frag: |
| 1028 | # Use IOCTLRequest |
| 1029 | pkt = SMB2_IOCTL_Request( |
| 1030 | FileId=self.PipeFileId, |
| 1031 | Flags="SMB2_0_IOCTL_IS_FSCTL", |
| 1032 | CtlCode="FSCTL_PIPE_TRANSCEIVE", |
| 1033 | ) |
| 1034 | pkt.Input = bytes(x) |
| 1035 | resp = self.ins.sr1(pkt, verbose=0) |
| 1036 | if SMB2_IOCTL_Response not in resp: |
| 1037 | raise ValueError("Failed reading IOCTL_Response ! %s" % resp.NTStatus) |
| 1038 | data = bytes(resp.Output) |
| 1039 | super(SMB_RPC_SOCKET, self).send(data) |
| 1040 | # Handle BUFFER_OVERFLOW (big DCE/RPC response) |
| 1041 | while resp.NTStatus == "STATUS_BUFFER_OVERFLOW" or data[3] & 2 != 2: |
| 1042 | # Retrieve DCE/RPC full size |
| 1043 | resp = self.ins.sr1( |
| 1044 | SMB2_Read_Request( |
| 1045 | FileId=self.PipeFileId, |
| 1046 | ), |
| 1047 | verbose=0, |
| 1048 | ) |
| 1049 | data = resp.Data |
| 1050 | super(SMB_RPC_SOCKET, self).send(data) |
| 1051 | else: |
| 1052 | # Use WriteRequest/ReadRequest |
| 1053 | pkt = SMB2_Write_Request( |
| 1054 | FileId=self.PipeFileId, |
| 1055 | ) |
| 1056 | pkt.Data = bytes(x) |
| 1057 | # We send the Write Request |
| 1058 | resp = self.ins.sr1(pkt, verbose=0) |
| 1059 | if SMB2_Write_Response not in resp: |
| 1060 | raise ValueError("Failed sending WriteResponse ! %s" % resp.NTStatus) |
| 1061 | # If fragmented, only read if it's the last. |
| 1062 | if is_frag and not x.pfc_flags.PFC_LAST_FRAG: |
| 1063 | return |
| 1064 | # We send a Read Request afterwards |
| 1065 | resp = self.ins.sr1( |
| 1066 | SMB2_Read_Request( |
| 1067 | FileId=self.PipeFileId, |
| 1068 | ), |
| 1069 | verbose=0, |
| 1070 | ) |
| 1071 | if SMB2_Read_Response not in resp: |
| 1072 | raise ValueError("Failed reading ReadResponse ! %s" % resp.NTStatus) |
| 1073 | super(SMB_RPC_SOCKET, self).send(resp.Data) |
| 1074 | # Handle fragmented response |
| 1075 | while resp.Data[3] & 2 != 2: # PFC_LAST_FRAG not set |
nothing calls this directly
no test coverage detected