void write_buffer(CFStringRef inData) { #ifdef DEBUG syslog(LOG_ERR,"Writing buffer to file."); #endif if (CFWriteStreamGetStatus(logStream)!=kCFStreamStatusOpen) { CFWriteStreamSetProperty(logStream,kCFStreamPropertyAppendToFile,kCFBooleanTrue); CFWriteStreamOpen(logStream); } if (!CFBooleanGetValue(doEncrypt)) { CFWriteStreamWrite(logStream,(const UInt8*)CFStringGetCStringPtr(inData,CFStringGetFastestEncoding(inData)),CFStringGetLength(inData)); return; } int buff_pos = 0; while (1) { int avail_space = 8-CFDataGetLength(encrypt_buffer); //space rem in buffer int rem_to_copy = CFStringGetLength(inData)-buff_pos; //stuff in data that needs to be copied int to_copy = rem_to_copy<avail_space?rem_to_copy:avail_space; //amount left to encryp, or avail space if (avail_space) { UInt8 tmp_buff[8]; CFStringGetBytes(inData,CFRangeMake(buff_pos,to_copy),kCFStringEncodingNonLossyASCII,0,false,tmp_buff,8,NULL); CFDataAppendBytes(encrypt_buffer,tmp_buff,to_copy); avail_space -= to_copy; if (avail_space>0) // small buffer? still space left? break; buff_pos += to_copy; //move along the buffer } UInt8 enc_buff[8]; BF_ecb_encrypt(CFDataGetBytePtr(encrypt_buffer),enc_buff,&encrypt_bf_key,BF_ENCRYPT); CFWriteStreamWrite(logStream,enc_buff,8); CFDataDeleteBytes(encrypt_buffer,CFRangeMake(0,8)); if (buff_pos==CFStringGetLength(inData)) //just in case buffer happens to fit perfectly break; } return; }
int SocketStreamHandle::platformSend(const char* data, int length) { if (!CFWriteStreamCanAcceptBytes(m_writeStream.get())) return 0; return CFWriteStreamWrite(m_writeStream.get(), reinterpret_cast<const UInt8*>(data), length); }
void Caching_Stream::streamEndEncountered() { if (m_fileOutput) { delete m_fileOutput, m_fileOutput = 0; } if (m_cacheable) { if (m_writable) { CS_TRACE("Successfully cached the stream\n"); CS_TRACE_CFURL(m_fileUrl); // We only write the meta data if the stream was successfully streamed. // In that way we can use the meta data as an indicator that there is a file to stream. if (!m_cacheMetaDataWritten) { CFWriteStreamRef writeStream = CFWriteStreamCreateWithFile(kCFAllocatorDefault, m_metaDataUrl); if (writeStream) { if (CFWriteStreamOpen(writeStream)) { CFStringRef contentType = m_target->contentType(); UInt8 buf[1024]; CFIndex usedBytes = 0; if (contentType) { // It is possible that some streams don't provide a content type CFStringGetBytes(contentType, CFRangeMake(0, CFStringGetLength(contentType)), kCFStringEncodingUTF8, '?', false, buf, 1024, &usedBytes); } if (usedBytes > 0) { CS_TRACE("Writing the meta data\n"); CS_TRACE_CFSTRING(contentType); CFWriteStreamWrite(writeStream, buf, usedBytes); } CFWriteStreamClose(writeStream); } CFRelease(writeStream); } m_cacheable = false; m_writable = false; m_useCache = true; m_cacheMetaDataWritten = true; } } } if (m_delegate) { m_delegate->streamEndEncountered(); } }
tsk_size_t tnet_transport_send(const tnet_transport_handle_t *handle, tnet_fd_t from, const void* buf, tsk_size_t size) { tnet_transport_t *transport = (tnet_transport_t*)handle; int numberOfBytesSent = 0; if (!transport) { TSK_DEBUG_ERROR("Invalid transport handle."); goto bail; } const transport_socket_t* sock = getSocket(transport->context, from); if (TNET_SOCKET_TYPE_IS_STREAM(sock->type)) { if (!sock->cf_write_stream) { TNET_PRINT_LAST_ERROR("No stream found."); goto bail; } if (CFWriteStreamGetStatus(sock->cf_write_stream) == kCFStreamStatusNotOpen) { CFWriteStreamOpen(sock->cf_write_stream); } if ((numberOfBytesSent = CFWriteStreamWrite(sock->cf_write_stream, buf, (CFIndex) size)) <= 0) { TNET_PRINT_LAST_ERROR("Send have failed."); goto bail; } } else { if ((numberOfBytesSent = send(from, buf, size, 0)) <= 0) { TNET_PRINT_LAST_ERROR("Send have failed."); goto bail; } } bail: return numberOfBytesSent; }
/* static */ void _HttpContextHandleCanAcceptBytes(HttpContextRef context) { DBG(("Sending data to the view\n")); // Get the start of the buffer to send. const UInt8* start = CFDataGetBytePtr(context->_sendBytes); // Get number of bytes ready to be send int size = CFDataGetLength(context->_sendBytes); // Writing resets the timer. CFRunLoopTimerSetNextFireDate(context->_timer, CFAbsoluteTimeGetCurrent() + kTimeOutInSeconds); // If there data in the buffer to send, take care of sending the data. if (size != 0) { // Write all of the bytes redy to be sent CFIndex bytesWritten = CFWriteStreamWrite(context->_outStream, start, size); DBG(("%d bytes sent\n", bytesWritten)); // If successfully sent the data, remove the bytes from the buffer. if (bytesWritten > 0) CFDataDeleteBytes(context->_sendBytes, CFRangeMake(0, bytesWritten)); } }
static void writeDataToStream(mailstream_low * s) { struct mailstream_cfstream_data * cfstream_data; cfstream_data = (struct mailstream_cfstream_data *) s->data; cfstream_data->writeResult = CFWriteStreamWrite(cfstream_data->writeStream, cfstream_data->writeBuffer, cfstream_data->writeBufferSize); //fprintf(stderr, "data written %i\n", (int) cfstream_data->writeResult); }
ssize_t SSLImpl::send(const void *mem, size_t len, void *storage) { ssl_data_t *data = (ssl_data_t*)storage; if (!CFWriteStreamCanAcceptBytes(data->writeStream)) return 0; int rc = CFWriteStreamWrite(data->writeStream, (const UInt8 *)mem, len); if (rc < 0) { CFStreamError err = CFWriteStreamGetError(data->writeStream); report_error("SSL send failed", &err); return -1; } return rc; }
OSStatus TCPStream_CFNetwork::secureTransportWriteCallback (SSLConnectionRef connection, const void *data, size_t *dataLength) { auto actualStream = reinterpret_cast<TCPStream_CFNetwork const *>(connection); if (!CFWriteStreamCanAcceptBytes(actualStream->outputStream)) { *dataLength = 0; return errSSLWouldBlock; } auto bytesWritten = CFWriteStreamWrite(actualStream->outputStream, reinterpret_cast<UInt8 const *>(data), *dataLength); if (bytesWritten < *dataLength) { *dataLength = bytesWritten; return errSSLWouldBlock; } return noErr; }
// Internal function, write provided buffer as websocket frame [0x00 buffer 0xff] // CFIndex __WebSocketClientWriteFrame (WebSocketClientRef client, const UInt8 *buffer, CFIndex length) { CFIndex result = 0; if (client) { if (buffer) { if (length > 0) { if (CFWriteStreamCanAcceptBytes(client->write)) { CFIndex didWrite = CFWriteStreamWrite(client->write, (UInt8[]) { (UInt8) 0x00 }, 1); if (didWrite == 1) { result += didWrite; didWrite = CFWriteStreamWrite(client->write, buffer, length); if (didWrite == length) { result += didWrite; didWrite = CFWriteStreamWrite(client->write, (UInt8[]) { (UInt8) 0xff }, 1); if (didWrite == 1) { result += didWrite; } } } } }
CFIndex File_Output::write(const UInt8 *buffer, CFIndex bufferLength) { return CFWriteStreamWrite(m_writeStream, buffer, bufferLength); }
static krb5_error_code od_dump_entry(krb5_context kcontext, HDB *db, hdb_entry_ex *entry, void *data) { CFErrorRef error = NULL; CFDictionaryRef dict; CFStringRef fn, uuidstr; CFUUIDRef uuid; CFURLRef url; dict = HeimODDumpHdbEntry(&entry->entry, &error); if (dict == NULL) { if (error) CFRelease(error); return 0; } uuid = CFUUIDCreate(NULL); if (uuid == NULL) { krb5_warnx(kcontext, "out of memory"); CFRelease(dict); return 0; } uuidstr = CFUUIDCreateString(NULL, uuid); CFRelease(uuid); if (uuidstr == NULL) { krb5_warnx(kcontext, "out of memory"); CFRelease(dict); return 0; } fn = CFStringCreateWithFormat(NULL, NULL, CFSTR("%s/%@.plist"), (char *)data, uuidstr); CFRelease(uuidstr); if (fn == NULL) { krb5_warnx(kcontext, "out of memory"); CFRelease(dict); return 0; } url = CFURLCreateWithFileSystemPath(NULL, fn, kCFURLPOSIXPathStyle, false); CFRelease(fn); if (url == NULL) { krb5_warnx(kcontext, "out of memory"); CFRelease(dict); return 0; } CFDataRef xmldata = CFPropertyListCreateData(NULL, dict, kCFPropertyListXMLFormat_v1_0, 0, NULL); CFRelease(dict); if (xmldata == NULL) { CFRelease(url); krb5_warnx(kcontext, "out of memory"); return 0; } CFWriteStreamRef stream = CFWriteStreamCreateWithFile(NULL, url); if (stream) { if (CFWriteStreamOpen(stream)) CFWriteStreamWrite(stream, CFDataGetBytePtr(xmldata), CFDataGetLength(xmldata)); CFWriteStreamClose(stream); CFRelease(stream); } CFRelease(url); CFRelease(xmldata); return 0; }
void TCPStream_CFNetwork::writeData(const std::vector<UInt8> &data) { CFWriteStreamWrite(outputStream, data.data(), data.size()); }
/* MyUploadCallBack is the stream callback for the CFFTPStream during an upload operation. Its main purpose is to wait for space to become available in the FTP stream (the write stream), and then read bytes from the file stream (the read stream) and write them to the FTP stream. */ static void MyUploadCallBack(CFWriteStreamRef writeStream, CFStreamEventType type, void * clientCallBackInfo) { MyStreamInfo *info = (MyStreamInfo *)clientCallBackInfo; CFIndex bytesRead; CFIndex bytesAvailable; CFIndex bytesWritten; CFStreamError error; assert(writeStream != NULL); assert(info != NULL); assert(info->writeStream == writeStream); switch (type) { case kCFStreamEventOpenCompleted: fprintf(stderr, "Open complete\n"); break; case kCFStreamEventCanAcceptBytes: /* The first thing we do is check to see if there's some leftover data that we read in a previous callback, which we were unable to upload for whatever reason. */ if (info->leftOverByteCount > 0) { bytesRead = 0; bytesAvailable = info->leftOverByteCount; } else { /* If not, we try to read some more data from the file. CFReadStreamRead will return the number of bytes read, or -1 if an error occurs preventing any bytes from being read, or 0 if the stream's end was encountered. */ bytesRead = CFReadStreamRead(info->readStream, info->buffer, kMyBufferSize); if (bytesRead < 0) { fprintf(stderr, "CFReadStreamRead returned %ld\n", bytesRead); goto exit; } bytesAvailable = bytesRead; } // bytesWritten = 0; if (bytesAvailable == 0) { /* We've hit the end of the file being uploaded. Shut everything down. Previous versions of this sample would terminate the upload stream by writing zero bytes to the stream. After discussions with CF engineering, we've decided that it's better to terminate the upload stream by just closing the stream. */ fprintf(stderr, "\nEnd up uploaded file; closing down\n"); goto exit; } else { /* CFWriteStreamWrite returns the number of bytes successfully written, -1 if an error has occurred, or 0 if the stream has been filled to capacity (for fixed-length streams). If the stream is not full, this call will block until at least one byte is written. However, as we're in the kCFStreamEventCanAcceptBytes callback, we know that at least one byte can be written, so we won't block. */ bytesWritten = CFWriteStreamWrite(info->writeStream, info->buffer, bytesAvailable); if (bytesWritten > 0) { info->totalBytesWritten += bytesWritten; /* If we couldn't upload all the data that we read, we temporarily store the data in our MyStreamInfo context until our CFWriteStream callback is called again with a kCFStreamEventCanAcceptBytes event. Copying the data down inside the buffer is not the most efficient approach, but it makes the code significantly easier. */ if (bytesWritten < bytesAvailable) { info->leftOverByteCount = bytesAvailable - bytesWritten; memmove(info->buffer, info->buffer + bytesWritten, info->leftOverByteCount); } else { info->leftOverByteCount = 0; } } else if (bytesWritten < 0) { fprintf(stderr, "CFWriteStreamWrite returned %ld\n", bytesWritten); /* If CFWriteStreamWrite failed, the write stream is dead. We will clean up when we get kCFStreamEventErrorOccurred. */ } } /* Print a status update if we made any forward progress. */ if ( (bytesRead > 0) || (bytesWritten > 0) ) { fprintf(stderr, "\rRead %7ld bytes; Wrote %8ld bytes", bytesRead, info->totalBytesWritten); } break; case kCFStreamEventErrorOccurred: error = CFWriteStreamGetError(info->writeStream); fprintf(stderr, "CFReadStreamGetError returned (%ld, %ld)\n", error.domain, error.error); goto exit; case kCFStreamEventEndEncountered: fprintf(stderr, "\nUpload complete\n"); goto exit; default: fprintf(stderr, "Received unexpected CFStream event (%ld)", type); break; } return; exit: MyStreamInfoDestroy(info); CFRunLoopStop(CFRunLoopGetCurrent()); return; }
/* MyDownloadCallBack is the stream callback for the CFFTPStream during a download operation. Its main purpose is to read bytes off the FTP stream for the file being downloaded and write them to the file stream of the destination file. */ static void MyDownloadCallBack(CFReadStreamRef readStream, CFStreamEventType type, void * clientCallBackInfo) { MyStreamInfo *info = (MyStreamInfo *)clientCallBackInfo; CFIndex bytesRead = 0, bytesWritten = 0; CFStreamError error; CFNumberRef cfSize; SInt64 size; float progress; assert(readStream != NULL); assert(info != NULL); assert(info->readStream == readStream); switch (type) { case kCFStreamEventOpenCompleted: /* Retrieve the file size from the CFReadStream. */ cfSize = CFReadStreamCopyProperty(info->readStream, kCFStreamPropertyFTPResourceSize); fprintf(stderr, "Open complete\n"); if (cfSize) { if (CFNumberGetValue(cfSize, kCFNumberSInt64Type, &size)) { fprintf(stderr, "File size is %" PRId64 "\n", size); info->fileSize = size; } CFRelease(cfSize); } else { fprintf(stderr, "File size is unknown\n"); assert(info->fileSize == 0); // It was set up this way by MyStreamInfoCreate. } break; case kCFStreamEventHasBytesAvailable: /* CFReadStreamRead will return the number of bytes read, or -1 if an error occurs preventing any bytes from being read, or 0 if the stream's end was encountered. */ bytesRead = CFReadStreamRead(info->readStream, info->buffer, kMyBufferSize); if (bytesRead > 0) { /* Just in case we call CFWriteStreamWrite and it returns without writing all the data, we loop until all the data is written successfully. Since we're writing to the "local" file system, it's unlikely that CFWriteStreamWrite will return before writing all the data, but it would be bad if we simply exited the callback because we'd be losing some of the data that we downloaded. */ bytesWritten = 0; while (bytesWritten < bytesRead) { CFIndex result; result = CFWriteStreamWrite(info->writeStream, info->buffer + bytesWritten, bytesRead - bytesWritten); if (result <= 0) { fprintf(stderr, "CFWriteStreamWrite returned %ld\n", result); goto exit; } bytesWritten += result; } info->totalBytesWritten += bytesWritten; } else { /* If bytesRead < 0, we've hit an error. If bytesRead == 0, we've hit the end of the file. In either case, we do nothing, and rely on CF to call us with kCFStreamEventErrorOccurred or kCFStreamEventEndEncountered in order for us to do our clean up. */ } if (info->fileSize > 0) { progress = 100*((float)info->totalBytesWritten/(float)info->fileSize); fprintf(stderr, "\r%.0f%%", progress); } break; case kCFStreamEventErrorOccurred: error = CFReadStreamGetError(info->readStream); fprintf(stderr, "CFReadStreamGetError returned (%ld, %ld)\n", error.domain, error.error); goto exit; case kCFStreamEventEndEncountered: fprintf(stderr, "\nDownload complete\n"); goto exit; default: fprintf(stderr, "Received unexpected CFStream event (%ld)", type); break; } return; exit: MyStreamInfoDestroy(info); CFRunLoopStop(CFRunLoopGetCurrent()); return; }