Hi,

I'm having trouble getting ns_uuencode to work properly. I initially
thought that it was broken because it only accepted 48 chars, but I then
realized that it is simply supposed to be a helper proc.

After figuring that out, I've still had trouble getting it to work for
binary content. It works fine for plain text content. I've been diving into
the code (linux aolserver 3.4 nsd8x) to figure out what is wrong. I don't
know C very well (yet) so I may be missing some stuff, but I think I found
a bug.


* I read a file with [open] [fconfigure -encoding binary] [read].
* The file is read in as binary and placed in a ByteArray in a Tcl_Object.
* I begin to manipulate the string into chunks of 48 chars to send to
  ns_uuencode
* Aolserver must convert the binary content into strings. It sees that some
  characters have values > 127 (therefore > 7bit) and converts the string to
  Utf via the Tcl_UniCharToUtf convert proc. This adds extra chars.
* I send the string to ns_uuencode. These extra chars make ns_uuencode
  think that the string is longer than it is. (Not to mention that they
  make the output from ns_uuencode incorrect)

I've added a call inside NsTclHTUUEncodeCmd that converts the string from
Utf to iso8859-1 (NsUtf2Ext). This gets rid of those extra chars. I then
send the resulting Tcl_Dstring to Ns_HtuuEncode and it works.

Here's a brief diff on that fxn:

 NsTclHTUUEncodeCmd(ClientData dummy, Tcl_Interp *interp, int argc, char **argv)
 {
     char bufcoded[1 + (4 * 48) / 2];
+       char *ext;
     int  nbytes;
+    Tcl_DString              ds;
+       void            *enc;
+
+    Tcl_DStringInit(&ds);

     if (argc != 2) {
         Tcl_AppendResult(interp, "wrong # of args: should be \"",
                          argv[0], " string\"", NULL);
         return TCL_ERROR;
     }

+       // vinodk: decode Utf
+       // first get the encoding
+       enc = NsGetEnc("iso8859-1");
+       // convert. ext is a string, but may be invalid
+   //   if there are \0's in the binary file
+       //   ds will have the correct length and binary string
+       ext = NsUtf2Ext( enc, argv[1], &ds );

-    nbytes = strlen(argv[1]);
+    nbytes = ds.length;
     if (nbytes > 48) {
         Tcl_AppendResult(interp, "invalid string \"",
-                         argv[1], "\": must be less than 48 characters", NULL);
+                         ds.string, "\": must be less than 48 characters", NULL);
         return TCL_ERROR;
     }
-    Ns_HtuuEncode((unsigned char *) argv[1], nbytes, bufcoded);
+    Ns_HtuuEncode((unsigned char *) ds.string, nbytes, bufcoded);
     Tcl_SetResult(interp, bufcoded, TCL_VOLATILE);

+    Tcl_DStringFree(&ds);
+
     return TCL_OK;
 }


Is my thinking right here?

Thanks for any input,

Vinod
--
_____________________________
Vinod Kurup, MD
email: [EMAIL PROTECTED]
phone: 617.825.2485
cell:  617.359.5990
http://www.kurup.com
aim: vvkurup

Reply via email to