⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 dimeclient.cpp

📁 linux下简单对象应用协议的开发库
💻 CPP
字号:
/*	dimeclient.cpp	Example streaming DIME client for DIME server (dimeserver.cpp).	Supports three methods:	putData stores multiple data sets on the server and returns		named references to each data set	getData retrieves data sets given named references.	getImage is an example file-based image retrieval method	Change the endpoint in dime.h to your needs.	Copyright (C) 2000-2003 Robert A. van Engelen, Genivia, Inc.	All Rights Reserved.	Usage (server):	Start dimeserver on your host at port 8085 (see dimeserver.cpp):	dimeserver 8085 &	Usage (client):	dimeclient [-p] [-g] [-i] name ...	dimeclient		Without args retrieves image.jpg	dimeclient name		Retrieves image stored under name	dimeclient -p name1 name2 ...		Stores files name1, name2, etc. The storage keys are printed.		The keys provide access to the data on the server.	dimeclient -g name1 name2 ...		Retrieves files stored under keys name1, name2, etc.		The keys must correspond to the keys returned when storing		files. Files are stored locally under the key name.	Unix/Linux: add a sigpipe handler to avoid broken pipes.*/#include "soapH.h"#include "dime.nsmap"#include <assert.h>// use the default endpoint set in dime.h for demo:const char *endpoint = NULL;// use the localhost for -p and -g (put and get):const char *localhost = "http://localhost:8085";////////////////////////////////////////////////////////////////////////////////////	Forward decls//////////////////////////////////////////////////////////////////////////////////static void putData(struct soap*, int, char**);static void getData(struct soap*, int, char**);static void getImage(struct soap*, char*);static void saveData(ns__Data&, const char*);////////////////////////////////////////////////////////////////////////////////////	Streaming DIME attachment content handlers//////////////////////////////////////////////////////////////////////////////////static void *dime_read_open(struct soap*, void*, const char*, const char*, const char*);static void dime_read_close(struct soap*, void*);static size_t dime_read(struct soap*, void*, char*, size_t);static void *dime_write_open(struct soap*, const char*, const char*, const char*);static void dime_write_close(struct soap*, void*);static int dime_write(struct soap*, void*, const char*, size_t);////////////////////////////////////////////////////////////////////////////////////	Main//////////////////////////////////////////////////////////////////////////////////int main(int argc, char **argv){ struct soap soap;  // use HTTP 1.1 chunking  // HTTP chunking allows streaming of DIME content without requiring DIME attachment size to be set  // DIME attachments can be streamed without chunking ONLY if the attachment size is set  soap_init1(&soap, SOAP_IO_CHUNK);  // set DIME callbacks  soap.fdimereadopen = dime_read_open;  soap.fdimereadclose = dime_read_close;  soap.fdimeread = dime_read;  soap.fdimewriteopen = dime_write_open;  soap.fdimewriteclose = dime_write_close;  soap.fdimewrite = dime_write;  // connect timeout value (not supported by Linux)  soap.connect_timeout = 10;  // IO timeouts  soap.send_timeout = 30;  soap.recv_timeout = 30;  // Unix/Linux SIGPIPE, this is OS dependent:  // soap.accept_flags = SO_NOSIGPIPE;	// some systems like this  // soap.socket_flags = MSG_NOSIGNAL;	// others need this  // signal(SIGPIPE, sigpipe_handle);	// or a sigpipe handler (portable)  if (argc < 3)  { char *name;    if (argc < 2)      name = "image.jpg";    else      name = argv[1];    getImage(&soap, name);  }  else  { switch (argv[1][1])    { case 'p':	endpoint = localhost;        putData(&soap, argc, argv);        break;      case 'g':	endpoint = localhost;        getData(&soap, argc, argv);        break;      default:        fprintf(stderr, "Usage: [-p] [-g] name ...\n");	exit(0);    }  }  soap_destroy(&soap);  soap_end(&soap);  soap_done(&soap);  return SOAP_OK;}////////////////////////////////////////////////////////////////////////////////////	Helper functions//////////////////////////////////////////////////////////////////////////////////static void putData(struct soap *soap, int argc, char **argv){ arrayOfData data;  arrayOfName names;  data.resize(argc - 2);  for (int i = 2; i < argc; i++)  { data[i - 2].__ptr = (unsigned char*)argv[i];    // MUST set id or type to enable DIME    // zero size indicates streaming DIME (this requires HTTP chunking)    data[i - 2].type = "";  }  if (soap_call_ns__putData(soap, endpoint, NULL, &data, &names))    soap_print_fault(soap, stderr);  else  { printf("Data stored with keys:\n");    for (int j = 0; j < names.size(); j++)      printf("\t%s\n", names[j]);    printf("Use these keys to retrieve the data\n");  }}static void getData(struct soap *soap, int argc, char **argv){ arrayOfData data;  arrayOfName names;  names.resize(argc - 2);  for (int i = 2; i < argc; i++)    names[i - 2] = argv[i];  soap->user = (void*)names.__ptr;  if (soap_call_ns__getData(soap, endpoint, NULL, &names, &data))    soap_print_fault(soap, stderr);  else  { for (int j = 0; j < data.size(); j++)      if (!data[j].id)        saveData(data[j], argv[j + 2]);    printf("Data retrieved\n");  }}static void getImage(struct soap *soap, char *name){ ns__Data image;  arrayOfName temp;  temp.resize(1);  temp[0] = name;  soap->user = (void*)temp.__ptr;  if (soap_call_ns__getImage(soap, endpoint, NULL, name, image))    soap_print_fault(soap, stderr);  else if (image.id)  { if (image.__size)      printf("Got image %s size=%d type=%s through streaming DIME\n", name, image.__size, image.type?image.type:"");    else      printf("Got image %s type=%s through chunked streaming DIME\n", name, image.type?image.type:"");  }  else  { printf("Got image %s\n", name);    saveData(image, name);  }}static void saveData(ns__Data& data, const char *name){ char *buf = (char*)data.__ptr;  int len = data.__size;  FILE *fd = fopen(name, "wb");  if (!fd)  { fprintf(stderr, "Cannot save file %s\n", name);    return;  }  while (len)  { size_t nwritten = fwrite(buf, 1, len, fd);    if (!nwritten)    { fprintf(stderr, "Cannot write to %s\n", name);      return;    }    len -= nwritten;    buf += nwritten;  }  printf("Saved file %s\n", name);}////////////////////////////////////////////////////////////////////////////////////	Streaming DIME attachment content handlers//////////////////////////////////////////////////////////////////////////////////static void *dime_read_open(struct soap *soap, void *handle, const char *id, const char *type, const char *options){ FILE *fd;  // we should return NULL without setting soap->error if we don't want to use the streaming callback for this DIME attachment. The handle contains the non-NULL __ptr field value which should have been set in the application.  // return value of this function will be passed on to the fdimeread and fdimereadclose callbacks. The return value will not affect the __ptr field.  fd = fopen((char*)handle, "rb");  return (void*)fd;}static void dime_read_close(struct soap *soap, void *handle){ fclose((FILE*)handle);}static size_t dime_read(struct soap *soap, void *handle, char *buf, size_t len){ return fread(buf, 1, len, (FILE*)handle);}static void *dime_write_open(struct soap *soap, const char *id, const char *type, const char *options){ // we can return NULL without setting soap->error if we don't want to use the streaming callback for this DIME attachment  FILE *handle = NULL;  char *name;  // get file name from options (not '\0' terminated)  if (options)  { size_t len = ((unsigned char)options[2] << 8) | ((unsigned char)options[3]); // option string length    name = (char*)soap_malloc(soap, len + 1);    strncpy(name, options + 4, len);    name[len] = '\0';    handle = fopen(name, "wb");    if (!handle)    { soap->error = SOAP_EOF; // could not open file for writing      soap->errnum = errno; // get reason      return NULL;    }  }  else     soap->error = soap_receiver_fault(soap, "Cannot save to file, because no file name was present in attachment", NULL);  return (void*)handle;}static void dime_write_close(struct soap *soap, void *handle){ fclose((FILE*)handle);}static int dime_write(struct soap *soap, void *handle, const char *buf, size_t len){ while (len)  { size_t nwritten = fwrite(buf, 1, len, (FILE*)handle);    if (!nwritten)    { soap->errnum = errno; // get reason      return SOAP_EOF;    }    len -= nwritten;    buf += nwritten;  }  return SOAP_OK;}////////////////////////////////////////////////////////////////////////////////////	ns__Data class//////////////////////////////////////////////////////////////////////////////////ns__Data::ns__Data(){ __ptr = NULL;  __size = 0;  id = NULL;  type = NULL;  options = NULL;  soap = NULL;}////////////////////////////////////////////////////////////////////////////////////	arrayOfData class//////////////////////////////////////////////////////////////////////////////////arrayOfData::arrayOfData(){ __ptr = NULL;  __size = 0;  soap = NULL;}arrayOfData::arrayOfData(struct soap *soap, int n){ __ptr = NULL;  __size = 0;  this->soap = soap;  resize(n);}arrayOfData::~arrayOfData(){ resize(0);}int arrayOfData::size(){ return __size;}void arrayOfData::resize(int n){ if (__ptr)  { if (soap) // if created by soap environment      soap_delete(soap, __ptr); // then delete    else      delete[] __ptr;  }  __size = n;  if (n <= 0)    __ptr = NULL;  else if (soap)    __ptr = soap_new_ns__Data(soap, n);  else    __ptr = new ns__Data[n];}ns__Data& arrayOfData::operator[](int i) const{ assert(__ptr && i >= 0 && i < __size);  return __ptr[i];}////////////////////////////////////////////////////////////////////////////////////	arrayOfName class//////////////////////////////////////////////////////////////////////////////////arrayOfName::arrayOfName(){ __ptr = NULL;  __size = 0;  soap = NULL;}arrayOfName::arrayOfName(struct soap *soap, int n){ __ptr = NULL;  __size = 0;  this->soap = soap;  resize(n);}arrayOfName::~arrayOfName(){ resize(0);}int arrayOfName::size(){ return __size;}void arrayOfName::resize(int n){ if (__ptr)  { if (soap) // if created by soap environment      soap_delete(soap, __ptr); // then delete    else      free(__ptr);  }  __size = n;  if (n <= 0)    __ptr = NULL;  else  { if (soap)      __ptr = (char**)soap_malloc(soap, sizeof(char*) * n);    else      __ptr = (char**)malloc(sizeof(char*) * n);    memset(__ptr, 0, n);  }}char*& arrayOfName::operator[](int i) const{ assert(__ptr && i >= 0 && i < __size);  return __ptr[i];}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -