Esempio n. 1
0
// This function should return number of bytes read... not status.
static SIZE_OR_ERROR FS_r_given_bus(struct one_wire_query *owq)
{
	// Device locking occurs here
	struct parsedname *pn = PN(owq);
	SIZE_OR_ERROR read_or_error = 0;

	LEVEL_DEBUG("About to read <%s> extension=%d size=%d offset=%d",SAFESTRING(pn->path),(int) pn->extension,(int) OWQ_size(owq),(int) OWQ_offset(owq));

	if (KnownBus(pn) && BusIsServer(pn->selected_connection)) {
		/* The bus is not local... use a network connection instead */
		LEVEL_DEBUG("pid=%ld call ServerRead", pthread_self());

		// Read afar -- returns already formatted in buffer
		read_or_error = ServerRead(owq);
		LEVEL_DEBUG("back from server");
		//printf("FS_r_given_bus pid=%ld r=%d\n",pthread_self(), read_or_error);
	} else {
		STAT_ADD1(read_calls);	/* statistics */
		if (DeviceLockGet(pn) == 0) {
			read_or_error = FS_r_local(owq);	// this returns status
			DeviceLockRelease(pn);
			LEVEL_DEBUG("return=%d", read_or_error);
			if (read_or_error >= 0) {
				// local success -- now format in buffer
				read_or_error = OWQ_parse_output(owq);	// this returns nr. bytes
			}
		} else {
			LEVEL_DEBUG("Cannot lock bus to perform read") ;
			read_or_error = -EADDRINUSE;
		}
	}
	LEVEL_DEBUG("After read is performed (bytes or error %d)", read_or_error);
	Debug_OWQ(owq);
	return read_or_error;
}
Esempio n. 2
0
/* cm.ret is also set to an error <0 or the read length */
void *ReadHandler(struct handlerdata *hd, struct client_msg *cm, struct one_wire_query *owq)
{
	BYTE * retbuffer = NULL ;
	SIZE_OR_ERROR read_or_error;

	LEVEL_DEBUG("ReadHandler start");
	if (hd == NULL || owq == NULL || cm == NULL) {
		LEVEL_DEBUG("ReadHandler: illegal null inputs hd==%p owq==%p cm==%p", hd, owq, cm);
		return NULL;			// only sane response for bad inputs
	}

	LEVEL_DEBUG("ReadHandler: From Client sm->payload=%d sm->size=%d sm->offset=%d", hd->sm.payload, hd->sm.size, hd->sm.offset);

	if (hd->sm.payload >= PATH_MAX) {
		cm->ret = -EMSGSIZE;
	} else if ((hd->sm.size <= 0) || (hd->sm.size > MAX_OWSERVER_PROTOCOL_PAYLOAD_SIZE)) {
		cm->ret = -EMSGSIZE;
		LEVEL_DEBUG("ReadHandler: error hd->sm.size == %d", hd->sm.size);
	} else if ( BAD( OWQ_allocate_read_buffer(owq)) ) {	// allocate read buffer
		LEVEL_DEBUG("ReadHandler: can't allocate memory");
		cm->ret = -ENOBUFS;
	} else {
		struct parsedname *pn = PN(owq);

		if ( OWQ_size(owq) > (size_t) hd->sm.size ) {
			OWQ_size(owq) = hd->sm.size ;
		}
		OWQ_offset(owq) = hd->sm.offset ;

		LEVEL_DEBUG("ReadHandler: call FS_read_postparse on %s", pn->path);
		read_or_error = FS_read_postparse(owq);
		LEVEL_DEBUG("ReadHandler: FS_read_postparse read on %s return = %d", pn->path, read_or_error);

		Debug_OWQ(owq);

		if (read_or_error <= 0) {
			LEVEL_DEBUG("ReadHandler: FS_read_postparse error %d", read_or_error);
			cm->ret = read_or_error;
		} else {
			LEVEL_DEBUG("ReadHandler: FS_read_postparse ok size=%d", read_or_error);
			// make return size smaller (just large enough)
			cm->payload = read_or_error;
			cm->offset = hd->sm.offset;
			cm->size = read_or_error;
			cm->ret = read_or_error;
			/* Move this pointer, and let owfree remove it instead of OWQ_destroy() */
			retbuffer = (BYTE *)OWQ_buffer(owq);
			OWQ_buffer(owq) = NULL;
		}
	}
	LEVEL_DEBUG("ReadHandler: To Client cm->payload=%d cm->size=%d cm->offset=%d", cm->payload, cm->size, cm->offset);
	if ((cm->size > 0)) {
		Debug_Bytes("Data returned to client",(BYTE *) OWQ_buffer(owq),cm->size) ;
	}
	return retbuffer;
}
Esempio n. 3
0
/* Handles 3-peat */
static ZERO_OR_ERROR FS_write_post_stats(struct one_wire_query *owq)
{
	// Parse the data to be written
	ZERO_OR_ERROR input_or_error = OWQ_parse_input(owq);

	Debug_OWQ(owq);
	if (input_or_error < 0) {
		LEVEL_DEBUG("Error interpreting input value.") ;
		return input_or_error ;
	}
	return FS_write_post_input( owq ) ;
}
Esempio n. 4
0
// This function should return number of bytes read... not status.
// Works for all the virtual directories, like statistics, interface, ...
// Doesn't need three-peat and bus was already set or not needed.
static SIZE_OR_ERROR FS_r_virtual(struct one_wire_query *owq)
{
	struct parsedname *pn = PN(owq);
	SIZE_OR_ERROR read_status = 0;

	if (SpecifiedRemoteBus(pn)) {
		/* The bus is not local... use a network connection instead */
		// Read afar -- returns already formatted in buffer
		read_status = ServerRead(owq);
		LEVEL_DEBUG("back from server");
		Debug_OWQ(owq);
	} else {
		/* local bus -- any special locking needs? */
		STAT_ADD1(read_calls);	/* statistics */
		switch (pn->type) {
		case ePN_structure:
			read_status = FS_structure(owq);
			break;
		case ePN_interface:
			BUSLOCK(pn);
			read_status = FS_r_local(owq);	// this returns status
			BUSUNLOCK(pn);
			break;
		case ePN_statistics:
			// reading /statistics/read/tries.ALL
			// will cause a deadlock since it calls STAT_ADD1(read_array);
			// Should perhaps create a new mutex for this.
			// Comment out this STATLOCK until it's solved.
			// STATLOCK now done at time of actual read in ow_stats.c
			read_status = FS_r_local(owq);	// this returns status
			break;
		default:
			read_status = FS_r_local(owq);	// this returns status
		}
		if (read_status >= 0) {
			// local success -- now format in buffer
			read_status = OWQ_parse_output(owq);	// this returns nr. bytes
		}
	}
	LEVEL_DEBUG("return %d", read_status);
	return read_status;
}
Esempio n. 5
0
static SIZE_OR_ERROR OWQ_parse_output_ascii(struct one_wire_query *owq)
{
	Debug_OWQ(owq);
	return OWQ_length(owq);
}