skel_decode_test.c

Go to the documentation of this file.
00001 /**
00002  * @file skel_decode_test.c
00003  * A simple test program for exercising ccn_skeleton_decoder.
00004  * 
00005  * A CCNx program.
00006  *
00007  * Copyright (C) 2009 Palo Alto Research Center, Inc.
00008  *
00009  * This work is free software; you can redistribute it and/or modify it under
00010  * the terms of the GNU General Public License version 2 as published by the
00011  * Free Software Foundation.
00012  * This work is distributed in the hope that it will be useful, but WITHOUT ANY
00013  * WARRANTY; without even the implied warranty of MERCHANTABILITY or
00014  * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
00015  * for more details. You should have received a copy of the GNU General Public
00016  * License along with this program; if not, write to the
00017  * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
00018  * Boston, MA 02110-1301, USA.
00019  */
00020 #include <fcntl.h>
00021 #include <limits.h>
00022 #include <stddef.h>
00023 #include <stdio.h>
00024 #include <stdint.h>
00025 #include <stdlib.h>
00026 #include <string.h>
00027 #include <unistd.h>
00028 
00029 #include <ccn/charbuf.h>
00030 #include <ccn/coding.h>
00031 
00032 static const char *tt_name[8] = {
00033     [CCN_EXT] = "CCN_EXT",
00034     [CCN_TAG] = "CCN_TAG",
00035     [CCN_DTAG] = "CCN_DTAG",
00036     [CCN_ATTR] = "CCN_ATTR",
00037     [CCN_DATTR] = "CCN_DATTR",
00038     [CCN_BLOB] = "CCN_BLOB",
00039     [CCN_UDATA] = "CCN_UDATA",
00040     [CCN_NO_TOKEN] = "CCN_CLOSE"
00041 };
00042 
00043 #define SHOW_HEX_STATE 1
00044 
00045 static int
00046 process_test(unsigned char *data, size_t n, int flags)
00047 {
00048     struct ccn_skeleton_decoder skel_decoder = {0};
00049     struct ccn_skeleton_decoder *d = &skel_decoder;
00050     int res = 0;
00051     size_t s;
00052     d->state |= flags & CCN_DSTATE_PAUSE;
00053 retry:
00054     s = ccn_skeleton_decode(d, data, n);
00055     if (flags & SHOW_HEX_STATE)
00056         fprintf(stderr, "state = 0x%x\n", d->state);
00057     if (d->state < 0) {
00058         res = 1;
00059         fprintf(stderr, "error state %d after %d of %d chars\n",
00060             (int)d->state, (int)s, (int)n);
00061     }
00062     else if (s == 0) {
00063         fprintf(stderr, "nothing to do\n");
00064     }
00065     else {
00066         if (d->state & CCN_DSTATE_PAUSE)
00067             fprintf(stderr, "Token type %s(%d) at index %d; el %d nest %d; ",
00068                 tt_name[CCN_GET_TT_FROM_DSTATE(d->state)],
00069                 (int)d->numval,
00070                 (int)d->token_index,
00071                 (int)d->element_index,
00072                 (int)d->nest);
00073         if (s < n) {
00074             fprintf(stderr, "resuming at index %d\n", (int)d->index);
00075             data += s;
00076             n -= s;
00077             goto retry;
00078         }
00079         fprintf(stderr, "\n");
00080     }
00081     if (!CCN_FINAL_DSTATE(d->state)) {
00082         res = 1;
00083         fprintf(stderr, "incomplete state %d after %d of %d chars\n",
00084             (int)d->state, (int)s, (int)n);
00085     }
00086     return(res);
00087 }
00088 
00089 static int
00090 process_fd(int fd, int flags)
00091 {
00092     struct ccn_charbuf *c = ccn_charbuf_create();
00093     ssize_t len;
00094     int res = 0;
00095     for (;;) {
00096         unsigned char *p = ccn_charbuf_reserve(c, 80);
00097         if (p == NULL) {
00098             perror("ccn_charbuf_reserve");
00099             res = 1;
00100             break;
00101         }
00102         len = read(fd, p, c->limit - c->length);
00103         if (len <= 0) {
00104             if (len == -1) {
00105                 perror("read");
00106                 res = 1;
00107             }
00108             break;
00109         }
00110         c->length += len;
00111     }
00112     fprintf(stderr, " <!-- input is %6lu bytes -->\n", (unsigned long)c->length);
00113     res |= process_test(c->buf, c->length, flags);
00114     ccn_charbuf_destroy(&c);
00115     return(res);
00116 }
00117 
00118 
00119 static int
00120 process_file(char *path, int flags)
00121 {
00122     int fd = 0;
00123     int res = 0;
00124     if (0 != strcmp(path, "-")) {
00125         fd = open(path, O_RDONLY);
00126         if (-1 == fd) {
00127             perror(path);
00128             return(1);
00129         }
00130     }
00131     res = process_fd(fd, flags);
00132     if (fd > 0)
00133         close(fd);
00134     return(res);
00135 }
00136 
00137 int
00138 main(int argc, char **argv)
00139 {
00140     int i;
00141     int res = 0;
00142     int flags = 0;
00143     for (i = 1; argv[i] != 0; i++) {
00144         if (0 == strcmp(argv[i], "-d")) {
00145             flags |= CCN_DSTATE_PAUSE;
00146             continue;
00147         }
00148         if (0 == strcmp(argv[i], "-D")) {
00149             flags |= CCN_DSTATE_PAUSE | SHOW_HEX_STATE;
00150             continue;
00151         }
00152         fprintf(stderr, "<!-- Processing %s -->\n", argv[i]);
00153         res |= process_file(argv[i], flags);
00154     }
00155     return(res);
00156 }
00157 

Generated on Thu Feb 16 00:44:00 2012 for Content-Centric Networking in C by  doxygen 1.5.6