chiark / gitweb /
c81e5d6b915ae929b4442cf2e7873eb5b6f4fa35
[chiark-tcl.git] / hbytes / chop.c
1 /*
2  */
3
4 #include <string.h>
5
6 #include "hbytes.h"
7
8 static int strs1(Tcl_Interp *ip, int strc, Tcl_Obj *const *strv, int *l_r) {
9   int rc, l, i;
10
11   l= 0;
12   for (i=1; i<strc; i++) {
13     rc= Tcl_ConvertToType(ip,strv[i],&hbytes_type);
14     if (rc) return rc;
15     l += hbytes_len(OBJ_HBYTES(strv[i]));
16   }
17   *l_r= l;
18   return TCL_OK;
19 }
20
21 static void strs2(Byte *dest, int strc, Tcl_Obj *const *strv) {
22   int tl, i;
23   
24   for (i=1; i<strc; i++) {
25     tl= hbytes_len(OBJ_HBYTES(strv[i]));
26     memcpy(dest, hbytes_data(OBJ_HBYTES(strv[i])), tl);
27     dest += tl;
28   }
29 }
30
31 int do_hbytes_prepend(ClientData cd, Tcl_Interp *ip,
32                       HBytes_Var v, int strc, Tcl_Obj *const *strv) {
33   int rc, el;
34   Byte *dest;
35   
36   rc= strs1(ip,strc,strv,&el);  if (rc) return rc;
37   dest= hbytes_prepend(v.hb, el);
38   strs2(dest, strc,strv);
39   return TCL_OK;
40 }
41   
42 int do_hbytes_append(ClientData cd, Tcl_Interp *ip,
43                      HBytes_Var v, int strc, Tcl_Obj *const *strv) {
44   int rc, el;
45   Byte *dest;
46
47   rc= strs1(ip,strc,strv,&el);  if (rc) return rc;
48   dest= hbytes_append(v.hb, el);
49   strs2(dest,  strc,strv);
50   return TCL_OK;
51 }
52
53 int do_hbytes_concat(ClientData cd, Tcl_Interp *ip,
54                      int strc, Tcl_Obj *const *strv, HBytes_Value *result) {
55   int rc, l;
56   Byte *dest;
57   
58   rc= strs1(ip,strc,strv,&l);  if (rc) return rc;
59   dest= hbytes_arrayspace(result,l);
60   strs2(dest, strc,strv);
61   return TCL_OK;
62 }
63
64 static int underrun(Tcl_Interp *ip) { return staticerr(ip,"data underrun"); }
65
66 int do_hbytes_unprepend(ClientData cd, Tcl_Interp *ip,
67                         HBytes_Var v, int preflength, HBytes_Value *result) {
68   const Byte *rdata= hbytes_unprepend(v.hb, preflength);
69   if (!rdata) return underrun(ip);
70   hbytes_array(result, rdata, preflength);
71   return TCL_OK;
72 }
73
74 int do_hbytes_unappend(ClientData cd, Tcl_Interp *ip,
75                        HBytes_Var v, int suflength, HBytes_Value *result) {
76   const Byte *rdata= hbytes_unappend(v.hb, suflength);
77   if (!rdata) return underrun(ip);
78   hbytes_array(result, rdata, suflength);
79   return TCL_OK;
80 }
81
82 int do_hbytes_chopto(ClientData cd, Tcl_Interp *ip,
83                      HBytes_Var v, int newlength, HBytes_Value *result) {
84   int suflength= hbytes_len(v.hb) - newlength;
85   return do_hbytes_unappend(0,ip,v, suflength, result);
86 }