added first stupid example; will test it later;
This commit is contained in:
		
							parent
							
								
									11498689e3
								
							
						
					
					
						commit
						15fb867657
					
				
							
								
								
									
										14
									
								
								Makefile.am
									
									
									
									
									
								
							
							
						
						
									
										14
									
								
								Makefile.am
									
									
									
									
									
								
							| @ -1,18 +1,12 @@ | |||||||
| ## Process this file with automake to produce Makefile.in
 | ## Process this file with automake to produce Makefile.in
 | ||||||
| 
 | 
 | ||||||
| #if BUILD_EXAMPLES
 | if BUILD_EXAMPLES | ||||||
| #EXAMPLES = examples
 | EXAMPLES = examples | ||||||
| #else
 |  | ||||||
| #EXAMPLES = 
 |  | ||||||
| #endif
 |  | ||||||
| 
 |  | ||||||
| if BUILD_TESTS |  | ||||||
| TESTS = tests |  | ||||||
| else | else | ||||||
| TESTS = | EXAMPLES =  | ||||||
| endif | endif | ||||||
| 
 | 
 | ||||||
| SUBDIRS = include lib man $(TESTS) | SUBDIRS = include lib man $(EXAMPLES) | ||||||
| 
 | 
 | ||||||
| libsxmpdocdir = ${prefix}/doc/libsxmp | libsxmpdocdir = ${prefix}/doc/libsxmp | ||||||
| libsxmpdoc_DATA = \
 | libsxmpdoc_DATA = \
 | ||||||
|  | |||||||
							
								
								
									
										21
									
								
								configure.ac
									
									
									
									
									
								
							
							
						
						
									
										21
									
								
								configure.ac
									
									
									
									
									
								
							| @ -16,23 +16,14 @@ dnl  ***************** | |||||||
| dnl ***** options ***** | dnl ***** options ***** | ||||||
| dnl  ***************** | dnl  ***************** | ||||||
| 
 | 
 | ||||||
| #AC_ARG_ENABLE([build_examples], | AC_ARG_ENABLE([build_examples], | ||||||
| #    AS_HELP_STRING([--enable-build-examples], [Enable examples build])) |     AS_HELP_STRING([--enable-build-examples], [Enable examples build])) | ||||||
| 
 | 
 | ||||||
| #AS_IF([test "x$enable_build_examples" = "xyes"], [ | AS_IF([test "x$enable_build_examples" = "xyes"], [ | ||||||
| #  AC_DEFINE([BUILD_EXAMPLES], 1, [build of examples enabled]) |   AC_DEFINE([BUILD_EXAMPLES], 1, [build of examples enabled]) | ||||||
| #]) |  | ||||||
| 
 |  | ||||||
| #AM_CONDITIONAL(BUILD_EXAMPLES, test "x$enable_build_examples" = "xyes") |  | ||||||
| 
 |  | ||||||
| AC_ARG_ENABLE([build_tests], |  | ||||||
|     AS_HELP_STRING([--enable-build-tests], [Enable build of tests])) |  | ||||||
| 
 |  | ||||||
| AS_IF([test "x$enable_build_tests" = "xyes"], [ |  | ||||||
|   AC_DEFINE([BUILD_TESTS], 1, [build of tests enabled]) |  | ||||||
| ]) | ]) | ||||||
| 
 | 
 | ||||||
| AM_CONDITIONAL(BUILD_TESTS, test "x$enable_build_tests" = "xyes") | AM_CONDITIONAL(BUILD_EXAMPLES, test "x$enable_build_examples" = "xyes") | ||||||
| 
 | 
 | ||||||
| PKG_CHECK_MODULES(OPENSSL, [openssl]) | PKG_CHECK_MODULES(OPENSSL, [openssl]) | ||||||
| 
 | 
 | ||||||
| @ -61,4 +52,4 @@ lib/libsxmp.pc | |||||||
| lib/Makefile | lib/Makefile | ||||||
| include/Makefile | include/Makefile | ||||||
| man/Makefile | man/Makefile | ||||||
| tests/Makefile]) | examples/Makefile]) | ||||||
|  | |||||||
							
								
								
									
										2
									
								
								examples/.gitignore
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										2
									
								
								examples/.gitignore
									
									
									
									
										vendored
									
									
										Normal file
									
								
							| @ -0,0 +1,2 @@ | |||||||
|  | filelistc | ||||||
|  | filelistd | ||||||
							
								
								
									
										25
									
								
								examples/Makefile.am
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										25
									
								
								examples/Makefile.am
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,25 @@ | |||||||
|  | ## AUTOMAKE_OPTIONS = foreign
 | ||||||
|  | 
 | ||||||
|  | AM_CPPFLAGS = \
 | ||||||
|  | 	-DPACKAGE_LOCALE_DIR=\""$(localedir)"\" \
 | ||||||
|  | 	-DPACKAGE_SRC_DIR=\""$(srcdir)"\" \
 | ||||||
|  | 	-DPACKAGE_DATA_DIR=\""$(pkgdatadir)"\" \
 | ||||||
|  | 	-DCNFPATH=\""$(prefix)/etc"\" \
 | ||||||
|  | 	-I../include \
 | ||||||
|  | 	-I../lib | ||||||
|  | 
 | ||||||
|  | AM_CFLAGS = -Wall -g | ||||||
|  | 
 | ||||||
|  | # where to find libsxmp
 | ||||||
|  | libsxmp = ../lib/.libs/libsxmp.la | ||||||
|  | 
 | ||||||
|  | bin_PROGRAMS =  filelistd filelistc | ||||||
|  | 
 | ||||||
|  | filelistd_SOURCES = filelistd.c | ||||||
|  | filelistd_LDADD = $(LIBTDATA_LIBS) $(LIBSEXPR_LIBS) $(OPENSSL_LIBS) \
 | ||||||
|  | 	$(LIBUUID_LIBS) $(libsxmp) -lpthread | ||||||
|  | 
 | ||||||
|  | filelistc_SOURCES = filelistc.c | ||||||
|  | filelistc_LDADD = $(LIBTDATA_LIBS) $(LIBSEXPR_LIBS) $(OPENSSL_LIBS) \
 | ||||||
|  | 	$(LIBUUID_LIBS) $(libsxmp) -lpthread | ||||||
|  | 
 | ||||||
| @ -38,6 +38,10 @@ | |||||||
| 
 | 
 | ||||||
| #define DEFAULT_PORT  10240 | #define DEFAULT_PORT  10240 | ||||||
| 
 | 
 | ||||||
|  | #define READONLY_CHANNEL  8 | ||||||
|  | #define WRITE_CHANNEL     16 | ||||||
|  | #define CONTROL_CHANNEL   20 | ||||||
|  | 
 | ||||||
| #define DEBUG | #define DEBUG | ||||||
| #define FREE(x) { if (x) { free(x); x = NULL; } } | #define FREE(x) { if (x) { free(x); x = NULL; } } | ||||||
| #define MAX_STREAMS INT_MAX | #define MAX_STREAMS INT_MAX | ||||||
|  | |||||||
| @ -61,10 +61,386 @@ | |||||||
| #include <errno.h> | #include <errno.h> | ||||||
| 
 | 
 | ||||||
| #include "filelist.h" | #include "filelist.h" | ||||||
|  | #include "../config.h" | ||||||
|  | 
 | ||||||
|  | #define FULL_PROGRAM_NAME        "File lister client" | ||||||
|  | 
 | ||||||
|  | struct _remote_host { | ||||||
|  |   char *root_x509; | ||||||
|  |   char *user_x509; | ||||||
|  |   char *hostname; | ||||||
|  |   char *login; | ||||||
|  |   char *password; | ||||||
|  |   int port; | ||||||
|  |   sxhub_t *hub; | ||||||
|  |   sxlink_t *link; | ||||||
|  | }; | ||||||
|  | 
 | ||||||
|  | struct _icmd { | ||||||
|  |   int id; | ||||||
|  |   int opt; | ||||||
|  |   char *cmdname; | ||||||
|  |   int (*__fu)(FILE *, struct _remote_host *, const char *); | ||||||
|  | }; | ||||||
|  | 
 | ||||||
|  | /* supported commands */ | ||||||
|  | enum commands { | ||||||
|  |   __LISTDIR = 0, | ||||||
|  | }; | ||||||
|  | 
 | ||||||
|  | static int __remote_ls(FILE *, struct _remote_host *, const char *); | ||||||
|  | 
 | ||||||
|  | struct _icmd _tool[] = { | ||||||
|  |   { .id = __LISTDIR, .opt = 0, .cmdname = "ls", .__fu = __remote_ls }, | ||||||
|  |   { .id = 0, .opt = 0, .cmdname = NULL, .__fu = NULL }, | ||||||
|  | }; | ||||||
|  | 
 | ||||||
|  | /*
 | ||||||
|  |  * This function might be used to check supported RPC calls | ||||||
|  |  * i.e. for each channel type id this callback is called. | ||||||
|  |  * Whereas the place to check it with ID and description. | ||||||
|  |  * Should return SXE_SUCCESS if supported. | ||||||
|  |  */ | ||||||
|  | static int __rpcscheck_onclient(sxlink_t *l, int ch_tid, char *description) | ||||||
|  | { | ||||||
|  |   return SXE_SUCCESS; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | /* supplemetary functions to make code more readable */ | ||||||
|  | static int __close_dir_stream(sxchnl_t *c, int sid) | ||||||
|  | { | ||||||
|  |   int r = SXE_SUCCESS; | ||||||
|  |   char *remote_rpc; | ||||||
|  |   size_t remote_rpc_len; | ||||||
|  |   sxmsg_t *msg = NULL; | ||||||
|  | 
 | ||||||
|  |   remote_rpc_len = strlen("dir-close") + sizeof(char)*16; | ||||||
|  |   if(!(remote_rpc = malloc(remote_rpc_len))) return ENOMEM; | ||||||
|  |   else remote_rpc_len = snprintf(remote_rpc, remote_rpc_len, "(dir-close %d)", sid); | ||||||
|  | 
 | ||||||
|  |   r = sxmsg_send(c, remote_rpc, remote_rpc_len, &msg); | ||||||
|  |   if(r == SXE_RAPIDMSG) sxmsg_clean(msg); | ||||||
|  |   else if(r == SXE_REPLYREQ) r = sxmsg_return(msg, SXE_SUCCESS); | ||||||
|  | 
 | ||||||
|  |   return r; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | /* our commands or tools implementation */ | ||||||
|  | static int __remote_ls(FILE *fso, struct _remote_host *rh, const char *opts) | ||||||
|  | { | ||||||
|  |   char *remote_rpc; | ||||||
|  |   size_t remote_rpc_len; | ||||||
|  |   sxmsg_t *msg = NULL; | ||||||
|  |   sxchnl_t *rpc_channel = NULL; | ||||||
|  |   sexp_t *sx, *isx, *iisx; | ||||||
|  |   char *remote_reply = NULL, *dname, *dtype; | ||||||
|  |   int rrc = 0, stream_id = 0, i, ii; | ||||||
|  | 
 | ||||||
|  |   /* ok determine the lenght */ | ||||||
|  |   remote_rpc_len = strlen("dir-open") + 12*sizeof(char) + | ||||||
|  |     (opts ? strlen ("./") : strlen(opts)); | ||||||
|  |   if(!(remote_rpc = malloc(remote_rpc_len))) return ENOMEM; | ||||||
|  |   else remote_rpc_len = snprintf(remote_rpc, remote_rpc_len, | ||||||
|  |                                  "(dir-open \"%s\")", opts ? "./" : opts); | ||||||
|  | 
 | ||||||
|  |   /* firstly open the required channel with required type */ | ||||||
|  |   if(!(rpc_channel = sxchannel_open(rh->link, READONLY_CHANNEL))) { | ||||||
|  |     rrc = errno; | ||||||
|  |     goto __fini; | ||||||
|  |   } | ||||||
|  | 
 | ||||||
|  |   rrc = sxmsg_send(rpc_channel, remote_rpc, remote_rpc_len, &msg); | ||||||
|  |   if(rrc == SXE_RAPIDMSG || rrc == SXE_REPLYREQ) { | ||||||
|  |     remote_reply = strdup(sxmsg_payload(msg)); | ||||||
|  | 
 | ||||||
|  |     if(rrc == SXE_RAPIDMSG) sxmsg_clean(msg); | ||||||
|  |     else rrc = sxmsg_return(msg, SXE_SUCCESS); | ||||||
|  |   } | ||||||
|  | 
 | ||||||
|  |   if(!remote_reply && (rrc != 0 || rrc != SXE_SUCCESS)) goto __fini; | ||||||
|  |   else sx = parse_sexp(remote_reply, strlen(remote_reply)); | ||||||
|  | 
 | ||||||
|  |   if(!sx) { rrc = EINVAL; goto __fini; } | ||||||
|  | 
 | ||||||
|  |   /* ok, now we will take a pass with our received S expression */ | ||||||
|  |   rrc = EINVAL; | ||||||
|  |   SEXP_ITERATE_LIST(sx, isx, i) { | ||||||
|  |     if(isx->ty == SEXP_LIST) stream_id = -1; | ||||||
|  |     if(!i && strcmp(isx->val, "dir-stream")) stream_id = -1; | ||||||
|  | 
 | ||||||
|  |     if(i == 1 && !stream_id) stream_id = atoi(isx->val); | ||||||
|  |   } | ||||||
|  | 
 | ||||||
|  |   /* free all the stuff */ | ||||||
|  |   destroy_sexp(sx); | ||||||
|  |   free(remote_reply); remote_reply = NULL; | ||||||
|  | 
 | ||||||
|  |   if(stream_id < 0) goto __fini; | ||||||
|  |   else rrc = SXE_SUCCESS; | ||||||
|  | 
 | ||||||
|  |   free(remote_rpc); | ||||||
|  | 
 | ||||||
|  |   /* now we're ready to read contents from the remote host */ | ||||||
|  |   remote_rpc_len = strlen("dir-read") + sizeof(char)*32; | ||||||
|  |   if(!(remote_rpc = malloc(remote_rpc_len))) { rrc = ENOMEM; goto __fini; } | ||||||
|  |   else remote_rpc_len = snprintf(remote_rpc, remote_rpc_len, "(dir-read %d)", stream_id); | ||||||
|  | 
 | ||||||
|  |   /* print header */ | ||||||
|  |   fprintf(fso, "%-24s | %-12s\n", "Name", "Type"); | ||||||
|  |   fprintf(fso, "---------------------------------------\n"); | ||||||
|  |   while(1) { | ||||||
|  |     rrc = sxmsg_send(rpc_channel, remote_rpc, remote_rpc_len, &msg); | ||||||
|  | 
 | ||||||
|  |     if(rrc == SXE_RAPIDMSG || rrc == SXE_REPLYREQ) { | ||||||
|  |       remote_reply = strdup(sxmsg_payload(msg)); | ||||||
|  | 
 | ||||||
|  |       if(rrc == SXE_RAPIDMSG) sxmsg_clean(msg); | ||||||
|  |       else rrc = sxmsg_return(msg, SXE_SUCCESS); | ||||||
|  |     } else goto __fini; | ||||||
|  | 
 | ||||||
|  |     if(!remote_reply) goto __fini; | ||||||
|  |     else if(!(sx = parse_sexp(remote_reply, strlen(remote_reply)))) { | ||||||
|  |       rrc = ENOMEM; | ||||||
|  |       goto __fini; | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     rrc = EINVAL; | ||||||
|  |     SEXP_ITERATE_LIST(sx, isx, i) { | ||||||
|  |       if(!i && isx->ty == SEXP_LIST) { rrc = EINVAL; goto __fini; } | ||||||
|  |       if(!i && !strcmp(isx->val, "dir-end")) { | ||||||
|  |         rrc = __close_dir_stream(rpc_channel, stream_id); | ||||||
|  |         goto __fini; | ||||||
|  |       } | ||||||
|  | 
 | ||||||
|  |       if(i && isx->ty != SEXP_LIST) { rrc = EINVAL; goto __fini; } | ||||||
|  |       else if(i) { | ||||||
|  |         SEXP_ITERATE_LIST(isx, iisx, ii) { | ||||||
|  |           if(!ii) dname = iisx->val; | ||||||
|  |           else dtype = iisx->val; | ||||||
|  |         } | ||||||
|  |         fprintf(fso, "%-24s | %-12s\n", dname, dtype); | ||||||
|  |       } | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     /* free it */ | ||||||
|  |     destroy_sexp(sx); | ||||||
|  |     free(remote_reply); remote_reply = NULL; | ||||||
|  |   } | ||||||
|  | 
 | ||||||
|  |  __fini: | ||||||
|  |   if(remote_reply) free(remote_reply); | ||||||
|  |   if(remote_rpc) free(remote_rpc); | ||||||
|  |   i = SXE_SUCCESS; | ||||||
|  |   if(rpc_channel) i = sxchannel_close(rpc_channel); | ||||||
|  | 
 | ||||||
|  |   if(rrc == SXE_SUCCESS && i == SXE_SUCCESS) rrc = 0; | ||||||
|  | 
 | ||||||
|  |   return rrc; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | static int __remote_host_connect(struct _remote_host *rh) | ||||||
|  | { | ||||||
|  |   int r = 0; | ||||||
|  | 
 | ||||||
|  |   sxhub_set_channelcall(rh->hub, __rpcscheck_onclient); | ||||||
|  | 
 | ||||||
|  |   /* here we go, connect to the hist i.e. create a link to it */ | ||||||
|  |   rh->link = sxlink_connect(rh->hub, rh->hostname, rh->port, rh->user_x509, | ||||||
|  |                             rh->login, rh->password); | ||||||
|  |   if(!rh->link) r = errno; | ||||||
|  | 
 | ||||||
|  |   return r; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | static void __help_print(FILE *fso, const char *fmtname) | ||||||
|  | { | ||||||
|  |   fprintf(fso, "\n%s\n\n", FULL_PROGRAM_NAME); | ||||||
|  | 
 | ||||||
|  |   /* usage options */ | ||||||
|  |   fprintf(fso, "Usage:\n"); | ||||||
|  |   fprintf(fso, "\t%s -r | --root-x509 <path> -u | --user-x509 <path> -H | --hostname <ip or hostname>" | ||||||
|  |           " -l | --login <login> -P | --password <password> -c | --command <command>" | ||||||
|  |           " [-o | --command-options <options>] [-p | --port <port>]\n", fmtname); | ||||||
|  | 
 | ||||||
|  |   /* defaults */ | ||||||
|  |   fprintf(fso, "\t%s -h | --help\n", fmtname); | ||||||
|  |   fprintf(fso, "\t%s -v | --version\n", fmtname); | ||||||
|  | 
 | ||||||
|  |   /* options description */ | ||||||
|  |   fprintf(fso, "\nOptions:\n"); | ||||||
|  |   fprintf(fso, "\t%-33s Set pathname of the remote root X.509 public certificate.\n", "-r | --root-x509 <path>"); | ||||||
|  |   fprintf(fso, "\t%-33s Set pathname of the user X.509 public and private certificate.\n", | ||||||
|  |           "-u | --user-x509 <path>"); | ||||||
|  |   fprintf(fso, "\t%-33s Hostname or IP address of the remote host.\n", "-H | --hostname <ip or hostname>"); | ||||||
|  |   fprintf(fso, "\t%-33s Set remote login name.\n", "-l | --login <login>"); | ||||||
|  |   fprintf(fso, "\t%-33s Set remote user password.\n", "-P | --password <password>"); | ||||||
|  |   fprintf(fso, "\t%-33s Command to run on the remote host.\n", "-c | --command <command>"); | ||||||
|  |   fprintf(fso, "\t%-33s Options for a command to run on the remote host [default: NULL].\n", | ||||||
|  |           "-o | --command-options <options>"); | ||||||
|  |   fprintf(fso, "\t%-33s Remote host listening port number [default: %d].\n", | ||||||
|  |           "-p | --port <port>", DEFAULT_PORT); | ||||||
|  |   fprintf(fso, "\t%-33s Show help screen.\n", "-h | --help"); | ||||||
|  |   fprintf(fso, "\t%-33s Print version information.\n", "-v | --version"); | ||||||
|  |   return; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | static void __version_print(FILE *fso) | ||||||
|  | { | ||||||
|  |   fprintf(fso, "\nFile list example client.\n"); | ||||||
|  |   fprintf(fso, "Examples bundle for %s %s.\n", PACKAGE_NAME, PACKAGE_VERSION); | ||||||
|  |   return; | ||||||
|  | } | ||||||
| 
 | 
 | ||||||
| int main(int argc, char **argv) | int main(int argc, char **argv) | ||||||
| { | { | ||||||
|   int opt; |   char *rootca, *cert, *host, *cmd; | ||||||
|    |   char *login, *password, *options; | ||||||
|   return 0; |   int port = DEFAULT_PORT, opt, i = 0; | ||||||
|  |   int (*toolfunction)(FILE *, struct _remote_host *, const char *) = NULL; | ||||||
|  |   struct _remote_host *rh = malloc(sizeof(struct _remote_host)); | ||||||
|  |   sxhub_t *lhub; | ||||||
|  | 
 | ||||||
|  |   if(!rh) return ENOMEM; | ||||||
|  |   else memset(rh, 0, sizeof(struct _remote_host)); | ||||||
|  | 
 | ||||||
|  |   rootca = cert = host = cmd = NULL; | ||||||
|  |   login = password = options = NULL; | ||||||
|  | 
 | ||||||
|  |   while(1) { | ||||||
|  |     int option_index = 0; | ||||||
|  |     static struct option long_options[] = { | ||||||
|  |       /* These options a generic ones. */ | ||||||
|  |       {"help", no_argument, NULL, 'h'}, /* print out help and version info */ | ||||||
|  |       {"version", no_argument, NULL, 'v'}, /* just out a version info */ | ||||||
|  |       /*  The following options about settings . */ | ||||||
|  |       {"root-x509", required_argument, NULL, 'r'}, | ||||||
|  |       {"user-x509", required_argument, NULL, 'u'}, | ||||||
|  |       {"hostname", required_argument, NULL, 'H'}, | ||||||
|  |       {"port", required_argument, NULL, 'p'}, | ||||||
|  |       {"login", required_argument, NULL, 'l'}, | ||||||
|  |       {"password", required_argument, NULL, 'P'}, | ||||||
|  |       {"command", required_argument, NULL, 'c'}, | ||||||
|  |       {"command-options", required_argument, NULL, 'o'}, | ||||||
|  |       { NULL, 0, NULL, 0 }, | ||||||
|  |     }; | ||||||
|  | 
 | ||||||
|  |     if((opt = getopt_long(argc, argv, "hvr:u:H:p:l:P:c:o:", long_options, | ||||||
|  |                           &option_index)) == -1) break; | ||||||
|  | 
 | ||||||
|  |     switch(opt) { | ||||||
|  |     case 'h': | ||||||
|  |       __help_print(stdout, argv[0]); | ||||||
|  |       return 0; | ||||||
|  |       break; | ||||||
|  |     case 'v': | ||||||
|  |       __version_print(stdout); | ||||||
|  |       return 0; | ||||||
|  |       break; | ||||||
|  |     case 'r': | ||||||
|  |       if(!(rootca = strdup(optarg))) return ENOMEM; | ||||||
|  |       break; | ||||||
|  |     case 'u': | ||||||
|  |       if(!(cert = strdup(optarg))) return ENOMEM; | ||||||
|  |       break; | ||||||
|  |     case 'H': | ||||||
|  |       if(!(host = strdup(optarg))) return ENOMEM; | ||||||
|  |       break; | ||||||
|  |     case 'l': | ||||||
|  |       if(!(login = strdup(optarg))) return ENOMEM; | ||||||
|  |       break; | ||||||
|  |     case 'P': | ||||||
|  |       if(!(password = strdup(optarg))) return ENOMEM; | ||||||
|  |       break; | ||||||
|  |     case 'c': | ||||||
|  |       if(!(cmd = strdup(optarg))) return ENOMEM; | ||||||
|  |       break; | ||||||
|  |     case 'o': | ||||||
|  |       if(!(options = strdup(optarg))) return ENOMEM; | ||||||
|  |       break; | ||||||
|  |     case 'p': | ||||||
|  |       port = atoi(optarg); | ||||||
|  |       break; | ||||||
|  |     } | ||||||
|  |   } | ||||||
|  | 
 | ||||||
|  |   /* ok validate all before doing any stuff */ | ||||||
|  |   if(!rootca || !cert) { | ||||||
|  |     fprintf(stderr, "One or more x.509 certificates files not pointed.\n"); | ||||||
|  |     __help_print(stderr, argv[0]); | ||||||
|  |     return EINVAL; | ||||||
|  |   } | ||||||
|  |   if(!login || !password) { | ||||||
|  |     fprintf(stderr, "Login or password not pointed.\n"); | ||||||
|  |     __help_print(stderr, argv[0]); | ||||||
|  |     return EINVAL; | ||||||
|  |   } | ||||||
|  |   if(port <= 0) { | ||||||
|  |     fprintf(stderr, "Port number has invalid value.\n"); | ||||||
|  |     __help_print(stderr, argv[0]); | ||||||
|  |     return EINVAL; | ||||||
|  |   } | ||||||
|  |   /* ok, check up for the command */ | ||||||
|  |   if(!cmd) { | ||||||
|  |     fprintf(stderr, "No command given.\n"); | ||||||
|  |     __help_print(stderr, argv[0]); | ||||||
|  |     return EINVAL; | ||||||
|  |   } | ||||||
|  | 
 | ||||||
|  |   /* try to lookup it */ | ||||||
|  |   while(_tool[i].cmdname != NULL) { | ||||||
|  |     if(!strcmp(_tool[i].cmdname, cmd)) { | ||||||
|  |       if(_tool[i].opt && !options) { | ||||||
|  |         fprintf(stderr, "Command %s required options.\n", cmd); | ||||||
|  |         __help_print(stderr, argv[0]); | ||||||
|  |         return EINVAL; | ||||||
|  |       } | ||||||
|  |       toolfunction = _tool[i].__fu; | ||||||
|  |     } | ||||||
|  |   } | ||||||
|  |   if(!toolfunction) { | ||||||
|  |     fprintf(stderr, "No such function `%s' exist.\n", cmd); | ||||||
|  |     __help_print(stderr, argv[0]); | ||||||
|  |     return EINVAL; | ||||||
|  |   } | ||||||
|  | 
 | ||||||
|  |   /* initialize sxmp first */ | ||||||
|  |   sxmp_init(); /* init library */ | ||||||
|  |   lhub = sxhub_create(); /* create sxhub for link creation */ | ||||||
|  |   if(!lhub) return ENOMEM; | ||||||
|  | 
 | ||||||
|  |   i = sxhub_setsslserts(lhub, rootca, cert, cert); | ||||||
|  |   if(i) return i; | ||||||
|  | 
 | ||||||
|  |   /* ok setup our structure */ | ||||||
|  |   rh->port = port; | ||||||
|  |   rh->root_x509 = rootca; | ||||||
|  |   rh->user_x509 = cert; | ||||||
|  |   rh->hostname = host; | ||||||
|  |   rh->login = login; | ||||||
|  |   rh->password = password; | ||||||
|  |   rh->hub = lhub; | ||||||
|  | 
 | ||||||
|  |   i = __remote_host_connect(rh); | ||||||
|  |   if(i) { | ||||||
|  |     fprintf(stderr, "Failed to create link to %s@%s:%d with %d.\n", rh->login, rh->hostname, | ||||||
|  |             rh->port, i); | ||||||
|  |   } else { | ||||||
|  |     i = toolfunction(stdout, rh, options); | ||||||
|  |     if(i) fprintf(stderr, "Failed to run RPC on %s@%s:%d with %d.\n", rh->login, rh->hostname, | ||||||
|  |                   rh->port, i); | ||||||
|  | 
 | ||||||
|  |     sxlink_close(rh->link); /* don't forget to do this */ | ||||||
|  |   } | ||||||
|  | 
 | ||||||
|  |   /* free all stuff */ | ||||||
|  |   if(rh->root_x509) free(rh->root_x509); | ||||||
|  |   if(rh->user_x509) free(rh->user_x509); | ||||||
|  |   if(rh->hostname) free(rh->hostname); | ||||||
|  |   if(rh->password) free(rh->password); | ||||||
|  |   if(rh->login) free(rh->login); | ||||||
|  |   free(rh); | ||||||
|  | 
 | ||||||
|  |   if(lhub) sxhub_destroy(lhub); | ||||||
|  | 
 | ||||||
|  |   return i; | ||||||
| } | } | ||||||
|  | |||||||
| @ -169,7 +169,7 @@ static int __validate_sslpem(sxlink_t *l) | |||||||
|  * We don't overview this tuff here, just |  * We don't overview this tuff here, just | ||||||
|  * always allow. |  * always allow. | ||||||
|  */ |  */ | ||||||
| static int __secure_check(conn_t *co) | static int __secure_check(sxlink_t *l) | ||||||
| { | { | ||||||
|   return SXE_SUCCESS; |   return SXE_SUCCESS; | ||||||
| } | } | ||||||
| @ -385,8 +385,8 @@ int main(int argc, char **argv) | |||||||
|     return opt; |     return opt; | ||||||
|   } |   } | ||||||
| 
 | 
 | ||||||
|   /* we will add one channel with type id 12 "Demo rpc list" */ |   /* we will add one channel with type id READONLY_CHANNEL for read only operations */ | ||||||
|   opt = sxmp_rpclist_add(fulist, 12, "Demo RPC list", NULL); |   opt = sxmp_rpclist_add(fulist, READONLY_CHANNEL, "Read only operations", NULL); | ||||||
|   if(opt) { |   if(opt) { | ||||||
|     fprintf(stderr, "Failed to add typed RPC channel\n Failure.\n"); |     fprintf(stderr, "Failed to add typed RPC channel\n Failure.\n"); | ||||||
|     return opt; |     return opt; | ||||||
| @ -398,15 +398,15 @@ int main(int argc, char **argv) | |||||||
|   } |   } | ||||||
| 
 | 
 | ||||||
|   /* ok, let's add stream functions */ |   /* ok, let's add stream functions */ | ||||||
|   opt = sxmp_rpclist_add_function(fulist, 12, "dir-open", __dir_open); |   opt = sxmp_rpclist_add_function(fulist, READONLY_CHANNEL, "dir-open", __dir_open); | ||||||
|   if(opt) { |   if(opt) { | ||||||
|   __fail: |   __fail: | ||||||
|     fprintf(stderr, "Failed to add functions to typed RPC channel\n Failure.\n"); |     fprintf(stderr, "Failed to add functions to typed RPC channel\n Failure.\n"); | ||||||
|     return opt; |     return opt; | ||||||
|   } |   } | ||||||
|   opt = sxmp_rpclist_add_function(fulist, 12, "dir-read", __dir_read); |   opt = sxmp_rpclist_add_function(fulist, READONLY_CHANNEL, "dir-read", __dir_read); | ||||||
|   if(opt) goto __fail; |   if(opt) goto __fail; | ||||||
|   opt = sxmp_rpclist_add_function(fulist, 12, "dir-close", __dir_close); |   opt = sxmp_rpclist_add_function(fulist, READONLY_CHANNEL, "dir-close", __dir_close); | ||||||
|   if(opt) goto __fail; |   if(opt) goto __fail; | ||||||
| 
 | 
 | ||||||
|   /* ok, setup it */ |   /* ok, setup it */ | ||||||
|  | |||||||
| @ -1,46 +0,0 @@ | |||||||
| ## AUTOMAKE_OPTIONS = foreign
 |  | ||||||
| 
 |  | ||||||
| AM_CPPFLAGS = \
 |  | ||||||
| 	-DPACKAGE_LOCALE_DIR=\""$(localedir)"\" \
 |  | ||||||
| 	-DPACKAGE_SRC_DIR=\""$(srcdir)"\" \
 |  | ||||||
| 	-DPACKAGE_DATA_DIR=\""$(pkgdatadir)"\" \
 |  | ||||||
| 	-DCNFPATH=\""$(prefix)/etc"\" \
 |  | ||||||
| 	-I../include \
 |  | ||||||
| 	-I../lib |  | ||||||
| 
 |  | ||||||
| AM_CFLAGS = -Wall -g |  | ||||||
| 
 |  | ||||||
| # where to find libsntl
 |  | ||||||
| libsntl = ../lib/.libs/libsntl.la |  | ||||||
| 
 |  | ||||||
| if !COND_WIN32 |  | ||||||
| 
 |  | ||||||
| bin_PROGRAMS =  lv2sd lv2sc lv2ftpd lv2ftpc |  | ||||||
| 
 |  | ||||||
| lv2sd_SOURCES = lv2sd.c |  | ||||||
| lv2sd_LDADD = $(LIBTDATA_LIBS) $(LIBSEXPR_LIBS) $(OPENSSL_LIBS) \
 |  | ||||||
| 	$(LIBUUID_LIBS) $(libsntl) -lpthread |  | ||||||
| 
 |  | ||||||
| lv2sc_SOURCES = lv2sc.c |  | ||||||
| lv2sc_LDADD = $(LIBTDATA_LIBS) $(LIBSEXPR_LIBS) $(OPENSSL_LIBS) \
 |  | ||||||
| 	$(LIBUUID_LIBS) $(libsntl) -lpthread |  | ||||||
| 
 |  | ||||||
| lv2ftpd_SOURCES = lv2ftpd.c |  | ||||||
| lv2ftpd_LDADD = $(LIBTDATA_LIBS) $(LIBSEXPR_LIBS) $(OPENSSL_LIBS) \
 |  | ||||||
| 	$(LIBUUID_LIBS) $(libsntl) -lpthread |  | ||||||
| 
 |  | ||||||
| lv2ftpc_SOURCES = lv2ftpc.c |  | ||||||
| lv2ftpc_LDADD = $(LIBTDATA_LIBS) $(LIBSEXPR_LIBS) $(OPENSSL_LIBS) \
 |  | ||||||
| 	$(LIBUUID_LIBS) $(libsntl) -lpthread |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| else COND_WIN32 |  | ||||||
| 
 |  | ||||||
| bin_PROGRAMS =  lv2sc |  | ||||||
| 
 |  | ||||||
| lv2sc_SOURCES = lv2sc.c |  | ||||||
| lv2sc_LDADD = $(LIBTDATA_LIBS) $(LIBSEXPR_LIBS) $(OPENSSL_LIBS) \
 |  | ||||||
| 	$(LIBUUID_LIBS) $(libsntl) -lws2_32 |  | ||||||
| 
 |  | ||||||
| endif COND_WIN32 |  | ||||||
| 
 |  | ||||||
| @ -1,30 +0,0 @@ | |||||||
| 1. lv2ftp isn's serious, just a test and benchmark of the sntllv2 |  | ||||||
| 2. there are few stages: |  | ||||||
| 2.1 Simple v.1 |  | ||||||
|     This protocol is enough to donwload a directory subtree with files. |  | ||||||
| 2.1.1 Directory workout |  | ||||||
|     * Open directory stream: (dir-open "<dir-name>") |  | ||||||
|       * Return: error, or rapidly replies with (dir-stream <id>) |  | ||||||
|     * Read directory entry: (dir-read <id>) |  | ||||||
|       * Return: error, or rapidly replies with the following: |  | ||||||
|         * (dir-end <id>) |  | ||||||
|         * (dir-entry "<filename>" "<filetype>"), where filetype the following: |  | ||||||
|           * regular - regular file |  | ||||||
|           * directory - directory |  | ||||||
|           * block - block device |  | ||||||
|           * char - char device |  | ||||||
|           * fifo - named pipe |  | ||||||
|           * link - symbolic link |  | ||||||
|           * socket - socket |  | ||||||
|           * unknown - unknown file type |  | ||||||
|      * Close directory entry: (dir-close <id>) |  | ||||||
|        * Return: error or SNE_SUCCESS |  | ||||||
| 2.1.2 File workout |  | ||||||
|      * Open file: (file-open "<file-name>") |  | ||||||
|        * Return: error, or rapidly replies with (file-id <id>) |  | ||||||
|      * Get simple stat: (file-stat <id>) |  | ||||||
|        * Return error, or rapidle replies with (file-stat <id> <size>) |  | ||||||
|      * Read file data: (file-read <id> <offset>) |  | ||||||
|        * Return error, or rapidly replies with 30k(raw data, in base64 it will be more) (file-data <id> <offset> "<B64encoded data>") |  | ||||||
|      * Close file: (file-close <id>) |  | ||||||
|        * Return error or SNE_SUCCESS |  | ||||||
							
								
								
									
										352
									
								
								tests/lv2ftpc.c
									
									
									
									
									
								
							
							
						
						
									
										352
									
								
								tests/lv2ftpc.c
									
									
									
									
									
								
							| @ -1,352 +0,0 @@ | |||||||
| #include <stdio.h> |  | ||||||
| #define __USE_GNU |  | ||||||
| #include <stdlib.h> |  | ||||||
| #include <stdarg.h> |  | ||||||
| #include <sys/types.h> |  | ||||||
| 
 |  | ||||||
| #include <pthread.h> |  | ||||||
| #include <stdint.h> |  | ||||||
| #include <getopt.h> |  | ||||||
| #include <errno.h> |  | ||||||
| #include <assert.h> |  | ||||||
| #include <time.h> |  | ||||||
| 
 |  | ||||||
| #ifdef WIN32 |  | ||||||
| #include <Winsock2.h> |  | ||||||
| #include <signal.h> |  | ||||||
| #else |  | ||||||
| #include <sys/select.h> |  | ||||||
| #include <sys/wait.h> |  | ||||||
| #include <sys/socket.h> |  | ||||||
| #include <sys/resource.h> |  | ||||||
| #include <netdb.h> |  | ||||||
| #include <unistd.h> |  | ||||||
| #include <uuid/uuid.h> |  | ||||||
| #include <execinfo.h> |  | ||||||
| #include <netinet/in.h> |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #include <tdata/usrtc.h> |  | ||||||
| #include <sexpr/sexp.h> |  | ||||||
| #include <sntl/sntllv2.h> |  | ||||||
| #include <sntl/limits.h> |  | ||||||
| 
 |  | ||||||
| #define DEBUG |  | ||||||
| #define FREE(x) { if (x) { free(x); x = NULL; } } |  | ||||||
| /* define a little bit */ |  | ||||||
| #define DEFAULT_PORT  13133 |  | ||||||
| #define CHANNEL_COUNT 200 |  | ||||||
| #define CLIENT_COUNT 256 |  | ||||||
| #define MESSAGES_PER_SESSION 10000 |  | ||||||
| #define ITERATION_COUNT 1000 |  | ||||||
| 
 |  | ||||||
| #define FAILS_ONLY |  | ||||||
| 
 |  | ||||||
| struct testdata { |  | ||||||
|   int uc; |  | ||||||
|   pthread_mutex_t ulock; |  | ||||||
|   conn_t *co; |  | ||||||
| }; |  | ||||||
| 
 |  | ||||||
| static int __init_testdata(struct testdata *t, conn_t *co) |  | ||||||
| { |  | ||||||
|   t->uc = 0; |  | ||||||
|   pthread_mutex_init(&t->ulock, NULL); |  | ||||||
|   t->co = co; |  | ||||||
|   return 0; |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| static void __wait_completion(struct testdata *t) |  | ||||||
| { |  | ||||||
|   pthread_mutex_lock(&t->ulock); |  | ||||||
|   if(t->uc) { |  | ||||||
|     pthread_mutex_lock(&t->ulock); |  | ||||||
|   } |  | ||||||
|   return; |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| static int __set_typed_list_callback(conn_t *co, int ch, char *desc) |  | ||||||
| { |  | ||||||
|   printf("allowed channel %d (%s)\n", ch, desc); |  | ||||||
|   return SNE_SUCCESS; |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| static void *__addsthrd(void *a) |  | ||||||
| { |  | ||||||
|   struct testdata *t = a; |  | ||||||
|   conn_t *co = t->co; |  | ||||||
|   chnl_t *mch; |  | ||||||
|   sxmsg_t *msg; |  | ||||||
|   char mmbuf[1024]; |  | ||||||
|   size_t ln; |  | ||||||
|   int mr, i; |  | ||||||
| 
 |  | ||||||
|   pthread_mutex_lock(&t->ulock); |  | ||||||
|   t->uc++; |  | ||||||
|   pthread_mutex_unlock(&t->ulock); |  | ||||||
| 
 |  | ||||||
|   /* here we go */ |  | ||||||
|   mch = sxchannel_open(co, 12); |  | ||||||
|     if(!mch) { |  | ||||||
|     fprintf(stderr, "Failed to openchannel with %d\n", errno); |  | ||||||
|     goto __fini; |  | ||||||
|   } |  | ||||||
| 
 |  | ||||||
|   for(i = 0; i < MESSAGES_PER_SESSION; i++) { |  | ||||||
|     ln = snprintf(mmbuf, 1024, "(ar-add (10 10))"); |  | ||||||
|     mr = sxmsg_send(mch, mmbuf, ln, &msg); |  | ||||||
|     switch(mr) { |  | ||||||
|     case SNE_RAPIDMSG: |  | ||||||
|       //fprintf(stdout, "Rapidly replied: %s\n", (char *)sxmsg_payload(msg));
 |  | ||||||
|       sxmsg_clean(msg); |  | ||||||
|       break; |  | ||||||
|     case SNE_REPLYREQ: |  | ||||||
|       if(sxmsg_datalen(msg)) fprintf(stdout, "Replied (confirmation required): %s\n", |  | ||||||
|                                      (char *)sxmsg_payload(msg)); |  | ||||||
|       mr = sxmsg_return(msg, SNE_SUCCESS); |  | ||||||
|       fprintf(stderr, "mr = %d\n", mr); |  | ||||||
|       break; |  | ||||||
|     case SNE_SUCCESS: |  | ||||||
|       fprintf(stdout, "Success.\n"); |  | ||||||
|       break; |  | ||||||
|     default: |  | ||||||
|       fprintf(stderr, "ERROR: %d\n", mr); |  | ||||||
|       break; |  | ||||||
|     } |  | ||||||
|   } |  | ||||||
| 
 |  | ||||||
|   sxchannel_close(mch); |  | ||||||
| 
 |  | ||||||
|  __fini: |  | ||||||
|   t->uc--; |  | ||||||
|   if(t->uc <= 1) pthread_mutex_unlock(&t->ulock); |  | ||||||
| 
 |  | ||||||
|   return NULL; |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| int msg_send(chnl_t *ch, const char *mmbuf, size_t buflen, sxmsg_t *msg, char **rs) |  | ||||||
| { |  | ||||||
| #ifdef DEBUG |  | ||||||
|   printf("%s: got sx '%s'\n", __FUNCTION__, mmbuf); |  | ||||||
| #endif /* DEBUG */ |  | ||||||
| 
 |  | ||||||
|   int mr = sxmsg_send(ch, mmbuf, buflen, &msg); |  | ||||||
|   switch(mr) { |  | ||||||
|   case SNE_RAPIDMSG: |  | ||||||
|     if (rs) *rs = strdup((char *)sxmsg_payload(msg)); |  | ||||||
|     fprintf(stdout, "Rapidly replied: '%s'\n", (char *)sxmsg_payload(msg)); |  | ||||||
|     sxmsg_clean(msg); |  | ||||||
|     break; |  | ||||||
|   case SNE_REPLYREQ: |  | ||||||
|     if(sxmsg_datalen(msg)) fprintf(stdout, "Replied (confirmation required): %s\n", |  | ||||||
|                                    (char *)sxmsg_payload(msg)); |  | ||||||
|     mr = sxmsg_return(msg, SNE_SUCCESS); |  | ||||||
|     fprintf(stderr, "mr = %d\n", mr); |  | ||||||
|     break; |  | ||||||
|   case SNE_SUCCESS: |  | ||||||
|     fprintf(stdout, "Success.\n"); |  | ||||||
|     break; |  | ||||||
|   default: |  | ||||||
|     fprintf(stderr, "ERROR: %d\n", mr); |  | ||||||
|     break; |  | ||||||
|   } |  | ||||||
| #ifdef DEBUG |  | ||||||
|   // printf("%s: got rs %d\n", __FUNCTION__, mr);
 |  | ||||||
| #endif /* DEBUG */ |  | ||||||
|   return mr; |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| int main(int argc, char **argv) |  | ||||||
| { |  | ||||||
|   char *rootca = NULL, *cert = NULL; |  | ||||||
|   int port = DEFAULT_PORT; |  | ||||||
|   char *addr = NULL, *login = NULL, *password = NULL; |  | ||||||
|   int opt; |  | ||||||
|   conn_sys_t *ssys; |  | ||||||
|   conn_t *co; |  | ||||||
| 
 |  | ||||||
|   while((opt = getopt(argc, argv, "p:r:a:u:l:w:")) != -1) { |  | ||||||
|     switch(opt) { |  | ||||||
|     case 'p': |  | ||||||
|       port = atoi(optarg); |  | ||||||
|       break; |  | ||||||
|     case 'r': |  | ||||||
|       rootca = strdup(optarg); |  | ||||||
|       break; |  | ||||||
|     case 'a': |  | ||||||
|       addr = strdup(optarg); |  | ||||||
|       break; |  | ||||||
|     case 'u': |  | ||||||
|       cert = strdup(optarg); |  | ||||||
|       break; |  | ||||||
|     case 'l': |  | ||||||
|       login = strdup(optarg); |  | ||||||
|       break; |  | ||||||
|     case 'w': |  | ||||||
|       password = strdup(optarg); |  | ||||||
|       break; |  | ||||||
|     default: |  | ||||||
|       fprintf(stderr, "usage: %s [-p <PORTNUM>] -r <PATH to Root CA> -a <Server ip address> -u <PATH" |  | ||||||
|               " to SSL certificate> -l <User login> -w <User password>\n", argv[0]); |  | ||||||
|       return EINVAL; |  | ||||||
|     } |  | ||||||
|   } |  | ||||||
| 
 |  | ||||||
|   if(!rootca) { |  | ||||||
|     fprintf(stderr, "Root CA not pointed.\n Failure.\n"); |  | ||||||
|     return EINVAL; |  | ||||||
|   } |  | ||||||
| 
 |  | ||||||
|   if(!addr) { |  | ||||||
|     fprintf(stderr, "Server address not pointed.\n Failure.\n"); |  | ||||||
|     return EINVAL; |  | ||||||
|   } |  | ||||||
| 
 |  | ||||||
|   if(!cert) { |  | ||||||
|     fprintf(stderr, "User certificate not pointed.\n Failure.\n"); |  | ||||||
|     return EINVAL; |  | ||||||
|   } |  | ||||||
| 
 |  | ||||||
|   if(!login) { |  | ||||||
|     fprintf(stderr, "User login not pointed.\n Failure.\n"); |  | ||||||
|     return EINVAL; |  | ||||||
|   } |  | ||||||
| 
 |  | ||||||
|   if(!password) { |  | ||||||
|     fprintf(stderr, "User password not pointed.\n Failure.\n"); |  | ||||||
|     return EINVAL; |  | ||||||
|   } |  | ||||||
| 
 |  | ||||||
|   sntl_init(); |  | ||||||
|   /* all is fine let's init connection subsystem */ |  | ||||||
|   ssys = connections_create(); |  | ||||||
|   if(!ssys) { |  | ||||||
|     fprintf(stderr, "Subsystem init failed: %d\n", errno); |  | ||||||
|     return errno; |  | ||||||
|   } |  | ||||||
|   /* set working certificates */ |  | ||||||
|   opt = connections_setsslserts(ssys, rootca, cert, cert); |  | ||||||
|   if(opt) { |  | ||||||
|     fprintf(stderr, "Subsystem init failed (set SSL x.509 pems): %d\n", opt); |  | ||||||
|     return opt; |  | ||||||
|   } |  | ||||||
| 
 |  | ||||||
|   /* Tests */ |  | ||||||
|   struct timeval beg, end; |  | ||||||
|   /* try to open connection */ |  | ||||||
|   connections_set_channelcall(ssys, __set_typed_list_callback); |  | ||||||
| 
 |  | ||||||
|   gettimeofday(&beg, NULL); |  | ||||||
|   co = connection_link(ssys, addr, port, cert, login, password); |  | ||||||
| 
 |  | ||||||
|   if(!co) { |  | ||||||
|     fprintf(stderr, "Failed to connection with %d\n", errno); |  | ||||||
|     return errno; |  | ||||||
|   } |  | ||||||
|   gettimeofday(&end, NULL); |  | ||||||
| 
 |  | ||||||
|   if((end.tv_sec - beg.tv_sec) > 0) { |  | ||||||
|     printf("Seconds: %ld ", end.tv_sec - beg.tv_sec); |  | ||||||
|     printf("µS: %ld\n", end.tv_usec + (1000000 - beg.tv_usec)); |  | ||||||
|   } else printf("µS: %ld\n", end.tv_usec - beg.tv_usec); |  | ||||||
| 
 |  | ||||||
|   /* ok now we should open a channel */ |  | ||||||
|   chnl_t *testchannel = sxchannel_open(co, 12); |  | ||||||
| 
 |  | ||||||
|   if(!testchannel) { |  | ||||||
|     fprintf(stderr, "Failed to openchannel with %d\n", errno); |  | ||||||
|     return errno; |  | ||||||
|   } |  | ||||||
|   gettimeofday(&end, NULL); |  | ||||||
| 
 |  | ||||||
|   if((end.tv_sec - beg.tv_sec) > 0) { |  | ||||||
|     printf("Seconds: %ld ", end.tv_sec - beg.tv_sec); |  | ||||||
|     printf("µS: %ld\n", end.tv_usec + (1000000 - beg.tv_usec)); |  | ||||||
|   } else printf("µS: %ld\n", end.tv_usec - beg.tv_usec); |  | ||||||
| 
 |  | ||||||
|   /* ok, send a message */ |  | ||||||
|   char mmbuf[1024]; |  | ||||||
|   char *s_ret = NULL; |  | ||||||
|   sxmsg_t *msg = NULL; |  | ||||||
|   size_t ln; |  | ||||||
|   int mr, ee, stid; |  | ||||||
|   sexp_t *sx_ret = NULL; |  | ||||||
| 
 |  | ||||||
|   ln = snprintf(mmbuf, 1024, "(dir-open \".\")"); |  | ||||||
|   mr = msg_send(testchannel, mmbuf, ln, msg, &s_ret); |  | ||||||
|   if (mr != SNE_RAPIDMSG) goto __finish; |  | ||||||
| 
 |  | ||||||
|   sx_ret = parse_sexp(s_ret, strlen(s_ret)); |  | ||||||
|   FREE(s_ret); |  | ||||||
|   if (!sx_ret || !sx_ret->list || strcmp(sx_ret->list->val, "dir-stream") || |  | ||||||
|       !sx_ret->list->next || !sx_ret->list->next->val) |  | ||||||
|     goto __finish; |  | ||||||
| 
 |  | ||||||
|   stid = atoi(sx_ret->list->next->val); |  | ||||||
|   ln = snprintf(mmbuf, 1024, "(dir-read %d)", stid); |  | ||||||
|   while (1) { |  | ||||||
|     mr = msg_send(testchannel, mmbuf, ln, msg, &s_ret); |  | ||||||
|     if (mr != SNE_RAPIDMSG) goto __finish; |  | ||||||
| 
 |  | ||||||
|     sx_ret = parse_sexp(s_ret, strlen(s_ret)); |  | ||||||
|     if (!sx_ret || !sx_ret->list || !sx_ret->list->val) |  | ||||||
|       goto __finish; |  | ||||||
| 
 |  | ||||||
|     if (!strcmp(sx_ret->list->val, "dir-end")) { |  | ||||||
|       ln = snprintf(mmbuf, 1024, "(dir-close %d)", stid); |  | ||||||
|       mr = msg_send(testchannel, mmbuf, ln, msg, &s_ret); |  | ||||||
|       break; |  | ||||||
|     } |  | ||||||
| #ifdef DEBUG |  | ||||||
|     printf("%s: '%s'\n", __FUNCTION__, s_ret); |  | ||||||
| #endif /* DEBUG */ |  | ||||||
|     FREE(s_ret); |  | ||||||
|   } |  | ||||||
| 
 |  | ||||||
|   // switch(mr) {
 |  | ||||||
|   // case SNE_RAPIDMSG:
 |  | ||||||
|   //   fprintf(stdout, "Rapidly replied: %s\n", (char *)sxmsg_payload(msg));
 |  | ||||||
|   //   sxmsg_clean(msg);
 |  | ||||||
|   //   break;
 |  | ||||||
|   // case SNE_REPLYREQ:
 |  | ||||||
|   //   if(sxmsg_datalen(msg)) fprintf(stdout, "Replied (confirmation required): %s\n",
 |  | ||||||
|   //                                  (char *)sxmsg_payload(msg));
 |  | ||||||
|   //   mr = sxmsg_return(msg, SNE_SUCCESS);
 |  | ||||||
|   //   fprintf(stderr, "mr = %d\n", mr);
 |  | ||||||
|   //   break;
 |  | ||||||
|   // case SNE_SUCCESS:
 |  | ||||||
|   //   fprintf(stdout, "Success.\n");
 |  | ||||||
|   //   break;
 |  | ||||||
|   // default:
 |  | ||||||
|   //   fprintf(stderr, "ERROR: %d\n", mr);
 |  | ||||||
|   //   break;
 |  | ||||||
|   // }
 |  | ||||||
| 
 |  | ||||||
| __finish: |  | ||||||
|   ee = sxchannel_close(testchannel); |  | ||||||
|   printf("ee = %d\n", ee); |  | ||||||
|   gettimeofday(&end, NULL); |  | ||||||
| 
 |  | ||||||
|   if((end.tv_sec - beg.tv_sec) > 0) { |  | ||||||
|     printf("Seconds: %ld ", end.tv_sec - beg.tv_sec); |  | ||||||
|     printf("µS: %ld\n", end.tv_usec + (1000000 - beg.tv_usec)); |  | ||||||
|   } else printf("µS: %ld\n", end.tv_usec - beg.tv_usec); |  | ||||||
|   // sleep(10);
 |  | ||||||
|   // /* ok, now we need to create many threads */
 |  | ||||||
|   // struct testdata trd;
 |  | ||||||
|   // pthread_t thrd;
 |  | ||||||
|   // int i;
 |  | ||||||
|   // __init_testdata(&trd, co);
 |  | ||||||
| 
 |  | ||||||
|   // for(i = 0; i < 256; i++)    pthread_create(&thrd, NULL, __addsthrd, &trd);
 |  | ||||||
| 
 |  | ||||||
|   // __wait_completion(&trd);
 |  | ||||||
| 
 |  | ||||||
|   connection_close(co); |  | ||||||
| 
 |  | ||||||
|   connections_destroy(ssys); |  | ||||||
| 
 |  | ||||||
|   sntl_finalize(); |  | ||||||
| 
 |  | ||||||
|   return 0; |  | ||||||
| } |  | ||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user