Main Page | Alphabetical List | Data Structures | Directories | File List | Data Fields | Globals

wmlsdasm.c

Go to the documentation of this file.
00001 /* ==================================================================== 
00002  * The Kannel Software License, Version 1.0 
00003  * 
00004  * Copyright (c) 2001-2008 Kannel Group  
00005  * Copyright (c) 1998-2001 WapIT Ltd.   
00006  * All rights reserved. 
00007  * 
00008  * Redistribution and use in source and binary forms, with or without 
00009  * modification, are permitted provided that the following conditions 
00010  * are met: 
00011  * 
00012  * 1. Redistributions of source code must retain the above copyright 
00013  *    notice, this list of conditions and the following disclaimer. 
00014  * 
00015  * 2. Redistributions in binary form must reproduce the above copyright 
00016  *    notice, this list of conditions and the following disclaimer in 
00017  *    the documentation and/or other materials provided with the 
00018  *    distribution. 
00019  * 
00020  * 3. The end-user documentation included with the redistribution, 
00021  *    if any, must include the following acknowledgment: 
00022  *       "This product includes software developed by the 
00023  *        Kannel Group (http://www.kannel.org/)." 
00024  *    Alternately, this acknowledgment may appear in the software itself, 
00025  *    if and wherever such third-party acknowledgments normally appear. 
00026  * 
00027  * 4. The names "Kannel" and "Kannel Group" must not be used to 
00028  *    endorse or promote products derived from this software without 
00029  *    prior written permission. For written permission, please  
00030  *    contact org@kannel.org. 
00031  * 
00032  * 5. Products derived from this software may not be called "Kannel", 
00033  *    nor may "Kannel" appear in their name, without prior written 
00034  *    permission of the Kannel Group. 
00035  * 
00036  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED 
00037  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 
00038  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 
00039  * DISCLAIMED.  IN NO EVENT SHALL THE KANNEL GROUP OR ITS CONTRIBUTORS 
00040  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,  
00041  * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT  
00042  * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR  
00043  * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,  
00044  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE  
00045  * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,  
00046  * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 
00047  * ==================================================================== 
00048  * 
00049  * This software consists of voluntary contributions made by many 
00050  * individuals on behalf of the Kannel Group.  For more information on  
00051  * the Kannel Group, please see <http://www.kannel.org/>. 
00052  * 
00053  * Portions of this software are based upon software originally written at  
00054  * WapIT Ltd., Helsinki, Finland for the Kannel project.  
00055  */ 
00056 
00057 /*
00058  *
00059  * wmlsdasm.c
00060  *
00061  * Author: Markku Rossi <mtr@iki.fi>
00062  *
00063  * Copyright (c) 2000 WAPIT OY LTD.
00064  *       All rights reserved.
00065  *
00066  * Disassembler for WMLScript byte-code.
00067  *
00068  */
00069 
00070 #include "wsint.h"
00071 #include "gwlib/gwlib.h"
00072 
00073 #include <sys/stat.h>
00074 
00075 /* TODO:
00076      - print pragmas
00077      - option to disassemble only a named external function
00078      - print constants in assembler => wsasm.c */
00079 
00080 /********************* Prototypes for static functions ******************/
00081 
00082 /* Print usage message to the stdout. */
00083 static void usage(void);
00084 
00085 /* Lookup the name of the function `index' from the function names
00086    section of the byte-code structure `bc'.  The function returns NULL
00087    if the function is internal. */
00088 const char *lookup_function(WsBc *bc, WsUInt8 index);
00089 
00090 /********************* Static variables *********************************/
00091 
00092 /* The name of the compiler program. */
00093 static char *program;
00094 
00095 /********************* Global functions *********************************/
00096 
00097 int main(int argc, char *argv[])
00098 {
00099     int i;
00100     int opt;
00101     WsBool print_constants = WS_FALSE;
00102     WsBool print_function_names = WS_FALSE;
00103     WsBool print_functions = WS_FALSE;
00104     WsUInt8 k;
00105     WsUInt16 j;
00106 
00107     program = strrchr(argv[0], '/');
00108     if (program)
00109         program++;
00110     else
00111         program = argv[0];
00112 
00113     /* Process command line arguments. */
00114     while ((opt = getopt(argc, argv, "cfnh")) != EOF) {
00115         switch (opt) {
00116         case 'c':
00117             print_constants = WS_TRUE;
00118             break;
00119 
00120         case 'f':
00121             print_functions = WS_TRUE;
00122             break;
00123 
00124         case 'n':
00125             print_function_names = WS_TRUE;
00126             break;
00127 
00128         case 'h':
00129             usage();
00130             exit(0);
00131             break;
00132 
00133         case '?':
00134             printf("Try `%s -h' for a complete list of options.\n",
00135                    program);
00136             exit(1);
00137         }
00138     }
00139 
00140     for (i = optind; i < argc; i++) {
00141         FILE *fp;
00142         struct stat stat_st;
00143         unsigned char *data;
00144         size_t data_len;
00145         WsBc *bc;
00146 
00147         if (stat(argv[i], &stat_st) < 0) {
00148             fprintf(stderr, "%s: could not access `%s': %s\n",
00149                     program, argv[i], strerror(errno));
00150             exit(1);
00151         }
00152         data_len = stat_st.st_size;
00153 
00154         data = ws_malloc(data_len);
00155         if (data == NULL) {
00156             fprintf(stderr, "%s: out of memory: %s\n",
00157                     program, strerror(errno));
00158             exit(1);
00159         }
00160 
00161         fp = fopen(argv[i], "rb");
00162         if (fp == NULL) {
00163             fprintf(stderr, "%s: could not open input file `%s': %s\n",
00164                     program, argv[i], strerror(errno));
00165             exit(1);
00166         }
00167 
00168         if (fread(data, 1, data_len, fp) != data_len) {
00169             fprintf(stderr, "%s: could not read file `%s': %s\n",
00170                     program, argv[i], strerror(errno));
00171             exit(1);
00172         }
00173         fclose(fp);
00174 
00175         /* Decode byte-code. */
00176         bc = ws_bc_decode(data, data_len);
00177         if (bc == NULL) {
00178             fprintf(stderr, "%s: invalid byte-code file `%s'\n",
00179                     program, argv[i]);
00180             continue;
00181         }
00182 
00183         /* Print all requested data. */
00184         printf("\n%s:\t%lu bytes\n\n", argv[i], (unsigned long) data_len);
00185 
00186         if (print_constants) {
00187             printf("Disassembly of section Constants:\n\n");
00188             for (j = 0; j < bc->num_constants; j++) {
00189                 printf("%4d:\t", j);
00190                 switch (bc->constants[j].type) {
00191                 case WS_BC_CONST_TYPE_INT:
00192                     printf("%ld\n", (long) bc->constants[j].u.v_int);
00193                     break;
00194 
00195                 case WS_BC_CONST_TYPE_FLOAT32:
00196                     printf("%f\n", bc->constants[j].u.v_float);
00197                     break;
00198 
00199                 case WS_BC_CONST_TYPE_FLOAT32_NAN:
00200                     printf("NaN\n");
00201                     break;
00202 
00203                 case WS_BC_CONST_TYPE_FLOAT32_POSITIVE_INF:
00204                     printf("+infinity\n");
00205                     break;
00206 
00207                 case WS_BC_CONST_TYPE_FLOAT32_NEGATIVE_INF:
00208                     printf("-infinity\n");
00209                     break;
00210 
00211                 case WS_BC_CONST_TYPE_UTF8_STRING:
00212                     {
00213                         size_t pos = 0;
00214                         size_t column = 8;
00215                         unsigned long ch;
00216 
00217                         printf("\"");
00218 
00219                         while (ws_utf8_get_char(&bc->constants[j].u.v_string,
00220                                                 &ch, &pos)) {
00221                             if (ch < ' ') {
00222                                 printf("\\%02lx", ch);
00223                                 column += 3;
00224                             } else if (ch <= 0xff) {
00225                                 printf("%c", (unsigned char) ch);
00226                                 column++;
00227                             } else {
00228                                 printf("\\u%04lx", ch);
00229                                 column += 5;
00230                             }
00231                             if (column >= 75) {
00232                                 printf("\"\n\t\"");
00233                                 column = 8;
00234                             }
00235                         }
00236                         printf("\"\n");
00237                     }
00238                     break;
00239 
00240                 case WS_BC_CONST_TYPE_EMPTY_STRING:
00241                     printf("\"\"\n");
00242                     break;
00243                 }
00244             }
00245         }
00246 
00247         if (print_function_names) {
00248             printf("Disassembly of section Function names:\n\n");
00249             for (k = 0; k < bc->num_function_names; k++)
00250                 printf("  %-40.40s%8d\n",
00251                        bc->function_names[k].name,
00252                        bc->function_names[k].index);
00253         }
00254 
00255         if (print_functions) {
00256             WsCompilerPtr compiler = ws_create(NULL);
00257 
00258             printf("Disassembly of section Functions:\n");
00259 
00260             for (k = 0; k < bc->num_functions; k++) {
00261                 const char *name = lookup_function(bc, k);
00262 
00263                 printf("\nFunction %u", (unsigned int) k);
00264 
00265                 if (name)
00266                     printf(" <%s>", name);
00267 
00268                 printf(":\n");
00269 
00270                 ws_asm_dasm(compiler, bc->functions[k].code,
00271                             bc->functions[k].code_size);
00272             }
00273 
00274             ws_destroy(compiler);
00275         }
00276 
00277         if (!print_constants && !print_function_names && !print_functions) {
00278             printf("Sections:\n\
00279                    Name\t\t   Items\n\
00280                    Constants\t%8d\n\
00281                    Pragmas\t%8d\n\
00282                    Function names\t%8d\n\
00283                    Functions\t%8d\n",
00284                    bc->num_constants,
00285                    bc->num_pragmas,
00286                    bc->num_function_names,
00287                    bc->num_functions);
00288         }
00289 
00290         ws_bc_free(bc);
00291     }
00292 
00293     return 0;
00294 }
00295 
00296 /********************* Static functions *********************************/
00297 
00298 static void usage(void)
00299 {
00300     printf("Usage: %s OPTION... FILE...\n\
00301            \n\
00302            -c            print constants\n\
00303            -f            disassemble functions\n\
00304            -n            print function names\n\
00305            -h            print this help message and exit successfully\n\
00306            \n",
00307            program);
00308 }
00309 
00310 
00311 const char *lookup_function(WsBc *bc, WsUInt8 index)
00312 {
00313     WsUInt8 i;
00314 
00315     for (i = 0; i < bc->num_function_names; i++)
00316         if (bc->function_names[i].index == index)
00317             return bc->function_names[i].name;
00318 
00319     return NULL;
00320 }
See file LICENSE for details about the license agreement for using, modifying, copying or deriving work from this software.