File:  [ELWIX - Embedded LightWeight unIX -] / libaitrpc / src / blob.c
Revision 1.1.2.4: download - view: text, annotated - select for diffs - revision graph
Thu Jun 24 11:01:46 2010 UTC (14 years ago) by misho
Branches: rpc1_0
finish blob

    1: #include "global.h"
    2: 
    3: 
    4: /*
    5:  * rpc_srv_blobCreate() Create map blob to memory region and return object
    6:  * @srv = RPC Server instance
    7:  * @len = BLOB length object
    8:  * return: NULL error or !=NULL allocated BLOB object
    9:  */
   10: inline rpc_blob_t *
   11: rpc_srv_blobCreate(rpc_srv_t * __restrict srv, int len)
   12: {
   13: 	rpc_blob_t *blob = NULL;
   14: 	char szFName[MAXPATHLEN];
   15: 	int f;
   16: 
   17: 	memset(szFName, 0, MAXPATHLEN);
   18: 	snprintf(szFName, MAXPATHLEN, "%s/BLOB-XXXXXXXX", srv->srv_blob.dir);
   19: 	f = mkstemp(szFName);
   20: 	if (f == -1) {
   21: 		LOGERR;
   22: 		return NULL;
   23: 	}
   24: 	if (lseek(f, len - 1, SEEK_SET) == -1) {
   25: 		LOGERR;
   26: 		close(f);
   27: 		unlink(szFName);
   28: 		return NULL;
   29: 	} else
   30: 		write(f, "", 1);
   31: 
   32: 	blob = malloc(sizeof(rpc_blob_t));
   33: 	if (!blob) {
   34: 		LOGERR;
   35: 		close(f);
   36: 		unlink(szFName);
   37: 		return NULL;
   38: 	}
   39: 
   40: 	blob->blob_data = mmap(NULL, len, PROT_READ | PROT_WRITE, MAP_SHARED, f, 0);
   41: 	if (blob->blob_data == MAP_FAILED) {
   42: 		LOGERR;
   43: 		free(blob);
   44: 		close(f);
   45: 		unlink(szFName);
   46: 		return NULL;
   47: 	} else
   48: 		close(f);
   49: 
   50: 	blob->blob_len = len;
   51: 	blob->blob_var = strtol(strrchr(szFName, '-') + 1, NULL, 16);
   52: 	return blob;
   53: }
   54: 
   55: /*
   56:  * rpc_srv_blobMap() Map blob to memory region 
   57:  * @srv = RPC Server instance
   58:  * @blob = Map to this BLOB element
   59:  * return: -1 error or 0 ok
   60:  */
   61: inline int
   62: rpc_srv_blobMap(rpc_srv_t * __restrict srv, rpc_blob_t * __restrict blob)
   63: {
   64: 	int f;
   65: 	struct stat sb;
   66: 	char szFName[MAXPATHLEN];
   67: 
   68: 	if (!blob) {
   69: 		rpc_SetErr(EINVAL, "Error:: invalid arguments ...\n");
   70: 		return -1;
   71: 	}
   72: 
   73: 	memset(szFName, 0, MAXPATHLEN);
   74: 	snprintf(szFName, MAXPATHLEN, BLOB_FILE, srv->srv_blob.dir, blob->blob_var);
   75: 	f = open(szFName, O_RDONLY);
   76: 	if (f == -1) {
   77: 		LOGERR;
   78: 		return -1;
   79: 	}
   80: 	if (fstat(f, &sb) == -1) {
   81: 		LOGERR;
   82: 		close(f);
   83: 		return -1;
   84: 	}
   85: 
   86: 	blob->blob_data = mmap(NULL, sb.st_size, PROT_READ, MAP_PRIVATE, f, 0);
   87: 	if (blob->blob_data == MAP_FAILED) {
   88: 		LOGERR;
   89: 		close(f);
   90: 		blob->blob_data = NULL;
   91: 		return -1;
   92: 	} else {
   93: 		blob->blob_len = sb.st_size;
   94: 		close(f);
   95: 
   96: 		madvise(blob->blob_data, sb.st_size, MADV_SEQUENTIAL);
   97: 	}
   98: 
   99: 	return 0;
  100: }
  101: 
  102: /*
  103:  * rpc_srv_blobUnmap() Unmap blob memory region 
  104:  * @blob = Mapped BLOB element
  105:  * return: none
  106:  */
  107: inline void
  108: rpc_srv_blobUnmap(rpc_blob_t * __restrict blob)
  109: {
  110: 	if (!blob || !blob->blob_data)
  111: 		rpc_SetErr(EINVAL, "Error:: invalid arguments ...\n");
  112: 	else {
  113: 		munmap(blob->blob_data, blob->blob_len);
  114: 		blob->blob_data = NULL;
  115: 		blob->blob_len = 0;
  116: 	}
  117: }
  118: 
  119: /*
  120:  * rpc_srv_blobFree() Free blob from disk & memory
  121:  * @srv = RPC Server instance
  122:  * @blob = Mapped BLOB element
  123:  * return: -1 error or 0 ok
  124:  */
  125: inline int
  126: rpc_srv_blobFree(rpc_srv_t * __restrict srv, rpc_blob_t * __restrict blob)
  127: {
  128: 	char szFName[MAXPATHLEN];
  129: 
  130: 	if (!blob) {
  131: 		rpc_SetErr(EINVAL, "Error:: invalid arguments ...\n");
  132: 		return -1;
  133: 	}
  134: 
  135: 	if (blob->blob_data)
  136: 		rpc_srv_blobUnmap(blob);
  137: 
  138: 	memset(szFName, 0, MAXPATHLEN);
  139: 	snprintf(szFName, MAXPATHLEN, BLOB_FILE, srv->srv_blob.dir, blob->blob_var);
  140: 	if (remove(szFName) == -1) {
  141: 		LOGERR;
  142: 		return -1;
  143: 	}
  144: 
  145: 	return 0;
  146: }
  147: 
  148: // ------------------------------------------------------------
  149: 
  150: /*
  151:  * rpc_srv_sendBLOB() Send mapped BLOB to client
  152:  * @cli = Client instance
  153:  * @blob = Mapped BLOB element
  154:  * return: -1 error, 0 ok
  155:  */
  156: int
  157: rpc_srv_sendBLOB(rpc_cli_t * __restrict cli, rpc_blob_t * __restrict blob)
  158: {
  159: 	int ret, len;
  160: 	uint8_t *pos;
  161: 
  162: 	if (!cli || !blob || !blob->blob_data) {
  163: 		rpc_SetErr(EINVAL, "Error:: invalid arguments ...\n");
  164: 		return -1;
  165: 	}
  166: 
  167: 	for (ret = blob->blob_len, pos = blob->blob_data; ret > 0; ret -= len, pos += len)
  168: 		if ((len = send(cli->cli_sock, pos, ret > BLOBSIZ ? BLOBSIZ : ret, 0)) == -1) {
  169: 			LOGERR;
  170: 			return -1;
  171: 		}
  172: 
  173: 	return ret;
  174: }
  175: 
  176: /*
  177:  * rpc_srv_recvBLOB() Receive BLOB from client
  178:  * @cli = Client instance
  179:  * @blob = Mapped BLOB element
  180:  * return: -1 error, 0 ok, >0 unreceived data from client, may be error?
  181:  */
  182: int
  183: rpc_srv_recvBLOB(rpc_cli_t * __restrict cli, rpc_blob_t * __restrict blob)
  184: {
  185: 	int ret, len;
  186: 	uint8_t *pos;
  187: 	fd_set fds;
  188: 	struct timeval tv = { DEF_RPC_TIMEOUT, 0 };
  189: 
  190: 	if (!cli || !blob || !blob->blob_data) {
  191: 		rpc_SetErr(EINVAL, "Error:: invalid arguments ...\n");
  192: 		return -1;
  193: 	}
  194: 
  195: 	for (ret = blob->blob_len, pos = blob->blob_data; ret > 0; ret -= len, pos += len) {
  196: 		FD_ZERO(&fds);
  197: 		FD_SET(cli->cli_sock, &fds);
  198: 		len = select(cli->cli_sock + 1, &fds, NULL, NULL, &tv);
  199: 		if (len < 1) {
  200: 			LOGERR;
  201: 			return -1;
  202: 		}
  203: 
  204: 		if ((len = recv(cli->cli_sock, pos, BLOBSIZ, 0)) == -1) {
  205: 			LOGERR;
  206: 			return -1;
  207: 		}
  208: 	}
  209: 
  210: 	return ret;
  211: }

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>