1 /**
2  * @namespace   biew
3  * @file        biewutil.c
4  * @brief       This file contains useful primitives of BIEW project.
5  * @version     -
6  * @remark      this source file is part of Binary vIEW project (BIEW).
7  *              The Binary vIEW (BIEW) is copyright (C) 1995 Nickols_K.
8  *              All rights reserved. This software is redistributable under the
9  *              licence given in the file "Licence.en" ("Licence.ru" in russian
10  *              translation) distributed in the BIEW archive.
11  * @note        Requires POSIX compatible development system
12  *
13  * @author      Nickols_K
14  * @since       1995
15  * @note        Development, fixes and improvements
16 **/
17 #include <ctype.h>
18 #include <string.h>
19 #include <stdlib.h>
20 #include <stdio.h>
21 #include <limits.h>
22 #include <stdarg.h>
23 
24 #include "bmfile.h"
25 #include "biewutil.h"
26 #include "bconsole.h"
27 #include "tstrings.h"
28 #include "biewlib/biewlib.h"
29 #include "biewlib/pmalloc.h"
30 
31 tBool DumpMode = False;
32 tBool EditMode = False;
33 
GetBool(tBool _bool)34 int __FASTCALL__ GetBool(tBool _bool) { return _bool ? TWC_CHECK_CHAR : TWC_DEF_FILLER; }
35 
FFreeArr(void ** arr,unsigned n)36 void FFreeArr(void ** arr,unsigned n)
37 {
38   unsigned i;
39   for(i = 0;i < n;i++) PFREE(arr[i]);
40 }
41 
Summ(unsigned char * str,unsigned size)42 unsigned __FASTCALL__ Summ(unsigned char *str,unsigned size)
43 {
44   unsigned res,i;
45   res = 0;
46   for(i = 0;i < size;i++) res += str[i];
47   return res;
48 }
49 
GetBinary(char val)50 char * __FASTCALL__ GetBinary(char val)
51 {
52   static char bstr[9];
53   int i;
54   bstr[8] = 0;
55   for(i = 0;i < 8;i++) bstr[7-i] = ((val >> i) & 1) + '0';
56   return bstr;
57 }
58 
59 #define GET2DIGIT(str,legs,val)\
60 {\
61   char *s = (char *)str;\
62   s[0] = legs[(((unsigned char)val) >> 4) & 0x0F];\
63   s[1] = legs[((unsigned char)val) & 0x0F];\
64 }
65 
Get2Digit(tUInt8 val)66 char * __FASTCALL__ Get2Digit(tUInt8 val)
67 {
68   static char str[3] = "  ";
69   const char *legs = &legalchars[2];
70   GET2DIGIT(str,legs,val);
71   return str;
72 }
73 
Get2SignDig(tInt8 val)74 char * __FASTCALL__ Get2SignDig(tInt8 val)
75 {
76   static char str[4] = "   ";
77   const char *legs = &legalchars[2];
78   str[0] = val >= 0 ? '+' : '-';
79   if(val < 0) val = abs(val);
80   GET2DIGIT(&str[1],legs,val);
81   return str;
82 }
83 
Get4Digit(tUInt16 val)84 char * __FASTCALL__ Get4Digit(tUInt16 val)
85 {
86   static char rstr[5] = "    ";
87   const char *legs = &legalchars[2];
88   unsigned char v;
89   v = val>>8;
90   GET2DIGIT(rstr,legs,v);
91   GET2DIGIT(&rstr[2],legs,val);
92   return rstr;
93 }
94 
Get4SignDig(tInt16 val)95 char * __FASTCALL__ Get4SignDig(tInt16 val)
96 {
97   static char rstr[6] = "     ";
98   const char *legs = &legalchars[2];
99   unsigned char v;
100   rstr[0] = val >= 0 ? '+' : '-';
101   if(val < 0) val = abs(val);
102   v = val>>8;
103   GET2DIGIT(&rstr[1],legs,v);
104   GET2DIGIT(&rstr[3],legs,val);
105   return rstr;
106 }
107 
Get8Digit(tUInt32 val)108 char * __FASTCALL__ Get8Digit(tUInt32 val)
109 {
110   static char rstr[9] = "        ";
111   const char *legs = &legalchars[2];
112   unsigned char v;
113   v = val>>24;
114   GET2DIGIT(rstr,legs,v);
115   v = val>>16;
116   GET2DIGIT(&rstr[2],legs,v);
117   v = val>>8;
118   GET2DIGIT(&rstr[4],legs,v);
119   GET2DIGIT(&rstr[6],legs,val);
120   return rstr;
121 }
122 
Get8SignDig(tInt32 val)123 char * __FASTCALL__ Get8SignDig(tInt32 val)
124 {
125   static char rstr[10] = "         ";
126   const char *legs = &legalchars[2];
127   unsigned char v;
128   rstr[0] = val >= 0 ? '+' : '-';
129   if(val < 0) val = labs(val);
130   v = val>>24;
131   GET2DIGIT(&rstr[1],legs,v);
132   v = val>>16;
133   GET2DIGIT(&rstr[3],legs,v);
134   v = val>>8;
135   GET2DIGIT(&rstr[5],legs,v);
136   GET2DIGIT(&rstr[7],legs,val);
137   return rstr;
138 }
139 
140 #ifdef INT64_C
Get16Digit(tUInt64 val)141 char * __FASTCALL__ Get16Digit(tUInt64 val)
142 {
143   static char rstr[17] = "                ";
144   const char *legs = &legalchars[2];
145   unsigned char v;
146   v = val>>56;
147   GET2DIGIT(rstr,legs,v);
148   v = val>>48;
149   GET2DIGIT(&rstr[2],legs,v);
150   v = val>>40;
151   GET2DIGIT(&rstr[4],legs,v);
152   v = val>>32;
153   GET2DIGIT(&rstr[6],legs,v);
154   v = val>>24;
155   GET2DIGIT(&rstr[8],legs,v);
156   v = val>>16;
157   GET2DIGIT(&rstr[10],legs,v);
158   v = val>>8;
159   GET2DIGIT(&rstr[12],legs,v);
160   GET2DIGIT(&rstr[14],legs,val);
161   return rstr;
162 }
163 
Get16SignDig(tInt64 val)164 char * __FASTCALL__ Get16SignDig(tInt64 val)
165 {
166   static char rstr[18] = "                 ";
167   const char *legs = &legalchars[2];
168   unsigned char v;
169   rstr[0] = val >= 0 ? '+' : '-';
170   if(val < 0) val = -val;
171   v = val>>56;
172   GET2DIGIT(&rstr[1],legs,v);
173   v = val>>48;
174   GET2DIGIT(&rstr[3],legs,v);
175   v = val>>40;
176   GET2DIGIT(&rstr[5],legs,v);
177   v = val>>32;
178   GET2DIGIT(&rstr[7],legs,v);
179   v = val>>24;
180   GET2DIGIT(&rstr[9],legs,v);
181   v = val>>16;
182   GET2DIGIT(&rstr[11],legs,v);
183   v = val>>8;
184   GET2DIGIT(&rstr[13],legs,v);
185   GET2DIGIT(&rstr[15],legs,val);
186   return rstr;
187 }
188 #else
Get16Digit(tUInt32 low,tUInt32 high)189 char * __FASTCALL__ Get16Digit(tUInt32 low,tUInt32 high)
190 {
191   static char rstr[17] = "                ";
192   const char *legs = &legalchars[2];
193   unsigned char v;
194   v = high>>24;
195   GET2DIGIT(rstr,legs,v);
196   v = high>>16;
197   GET2DIGIT(&rstr[2],legs,v);
198   v = high>>8;
199   GET2DIGIT(&rstr[4],legs,v);
200   GET2DIGIT(&rstr[6],legs,high);
201   v = low>>24;
202   GET2DIGIT(&rstr[8],legs,v);
203   v = low>>16;
204   GET2DIGIT(&rstr[10],legs,v);
205   v = low>>8;
206   GET2DIGIT(&rstr[12],legs,v);
207   GET2DIGIT(&rstr[14],legs,low);
208   return rstr;
209 }
210 
Get16SignDig(tInt32 low,tInt32 high)211 char * __FASTCALL__ Get16SignDig(tInt32 low,tInt32 high)
212 {
213   static char rstr[18] = "                 ";
214   const char *legs = &legalchars[2];
215   unsigned char v;
216   rstr[0] = high >= 0 ? '+' : '-';
217   if(high < 0) { low = -low; if(low!=0) high++; high = -high; }
218   v = high>>24;
219   GET2DIGIT(&rstr[1],legs,v);
220   v = high>>16;
221   GET2DIGIT(&rstr[3],legs,v);
222   v = high>>8;
223   GET2DIGIT(&rstr[5],legs,v);
224   GET2DIGIT(&rstr[7],legs,high);
225   v = low>>24;
226   GET2DIGIT(&rstr[9],legs,v);
227   v = low>>16;
228   GET2DIGIT(&rstr[11],legs,v);
229   v = low>>8;
230   GET2DIGIT(&rstr[13],legs,v);
231   GET2DIGIT(&rstr[15],legs,low);
232   return rstr;
233 }
234 #endif
235 
GetHexAnalog(char val)236 static char __NEAR__ __FASTCALL__ GetHexAnalog(char val)
237 {
238   return val >= '0' && val <= '9' ? val-'0' : ((toupper(val)-'A'+10)) & 0x0F;
239 }
240 
CompressHex(unsigned char * dest,const char * src,unsigned sizedest,tBool usespace)241 void __FASTCALL__ CompressHex(unsigned char * dest,const char * src,unsigned sizedest,tBool usespace)
242 {
243   unsigned i,j;
244   for(i = j = 0;j < sizedest;j++)
245   {
246       dest[j] = (GetHexAnalog(src[i]) << 4) | GetHexAnalog(src[i + 1]);
247       i += 2;	/* [dBorca] avoid ambiguous side-effects */
248       if(usespace) i++;
249   }
250 }
251 
ma_Build(int nitems,tBool interact)252 memArray * __FASTCALL__ ma_Build( int nitems, tBool interact )
253 {
254   memArray * ret;
255   ret = PMalloc(sizeof(memArray));
256   if(ret)
257   {
258     memset(ret,0,sizeof(memArray));
259     if(nitems)
260     {
261       ret->data = PMalloc(nitems*sizeof(char *));
262       if(ret->data)
263       {
264         ret->nSize = nitems;
265       }
266     }
267   }
268   else
269   {
270     if(interact) MemOutBox("List creation");
271   }
272   return ret;
273 }
274 
ma_Destroy(memArray * obj)275 void  __FASTCALL__ ma_Destroy(memArray *obj)
276 {
277   unsigned i;
278   for(i = 0;i < obj->nItems;i++)
279   {
280     PFREE(obj->data[i]);
281   }
282   PFREE(obj->data);
283   PFREE(obj);
284 }
285 
286 #define LST_STEP 16
287 
ma_AddData(memArray * obj,const void * udata,unsigned len,tBool interact)288 tBool  __FASTCALL__ ma_AddData(memArray *obj,const void *udata,unsigned len,tBool interact)
289 {
290   char *new_item;
291   if(obj->nSize > UINT_MAX - (LST_STEP+1)) return 0;
292   if(obj->nItems + 1 > obj->nSize)
293   {
294     void *ptr;
295     if(!obj->data) ptr = PMalloc((obj->nSize+LST_STEP)*sizeof(char *));
296     else           ptr = PRealloc(obj->data,sizeof(char *)*(obj->nSize+LST_STEP));
297     if(ptr)
298     {
299       obj->nSize = obj->nSize+LST_STEP;
300       obj->data = ptr;
301     }
302     else goto err;
303   }
304   new_item = PMalloc(len);
305   if(new_item)
306   {
307     memcpy(new_item,udata,len);
308     obj->data[obj->nItems++] = new_item;
309     return True;
310   }
311   else
312   {
313     err:
314     if(interact)
315     {
316       MemOutBox("Building list");
317     }
318   }
319   return False;
320 }
321 
ma_AddString(memArray * obj,const char * udata,tBool interact)322 tBool __FASTCALL__ ma_AddString(memArray *obj,const char *udata,tBool interact)
323 {
324   return ma_AddData(obj,udata,strlen(udata)+1,interact);
325 }
326 
ma_Display(memArray * obj,const char * title,int flg,unsigned defsel)327 int __FASTCALL__ ma_Display(memArray *obj,const char *title,int flg, unsigned defsel)
328 {
329   return CommonListBox((const char **)obj->data,obj->nItems,title,flg,defsel);
330 }
331