source: src/router/shared/utils.c @ 8709

Last change on this file since 8709 was 8709, checked in by eko, 5 years ago

maybe little better, but still need to be checked

File size: 85.4 KB
Line 
1//#define CDEBUG 1
2
3#include <stdio.h>
4#include <stdlib.h>
5#include <string.h>
6#include <errno.h>
7#include <net/if.h>
8#include <dirent.h>
9#include <unistd.h>
10#include <ctype.h>
11#include <syslog.h>
12#include <sys/socket.h>
13#include <sys/stat.h>
14#include <fcntl.h>
15#include <netinet/in.h>
16#include <stdarg.h>
17#include <sys/ioctl.h>
18#include <sys/sysinfo.h>
19#include <arpa/inet.h>
20#include <netdb.h>
21#include <resolv.h>
22#include <signal.h>
23
24
25
26#include <utils.h>
27#include <wlutils.h>
28#include <bcmnvram.h>
29#include <shutils.h>
30#include <cy_conf.h>
31#include <code_pattern.h>
32#include <bcmdevs.h>
33#include <net/route.h>
34#include <cy_conf.h>
35#include <bcmdevs.h>
36#include <linux/if_ether.h>
37//#include <linux/mii.h>
38#include <linux/sockios.h>
39#include <cymac.h>
40
41#define SIOCGMIIREG     0x8948  /* Read MII PHY register.       */
42#define SIOCSMIIREG     0x8949  /* Write MII PHY register.      */
43void show_hw_type (int type);
44
45struct mii_ioctl_data
46{
47  unsigned short phy_id;
48  unsigned short reg_num;
49  unsigned short val_in;
50  unsigned short val_out;
51};
52
53
54int
55getcpurev (void)
56{
57  FILE *fp = fopen ("/proc/cpuinfo", "rb");
58  if (fp == NULL)
59    {
60      return -1;
61    }
62  int cnt = 0;
63  int b = 0;
64  while (b != EOF)
65    {
66      b = getc (fp);
67      if (b == ':')
68        cnt++;
69      if (cnt == 3)
70        {
71          getc (fp);
72          char cpurev[13];
73          int i = 0;
74          for (i = 0; i < 12; i++)
75            cpurev[i] = getc (fp);
76          cpurev[i] = 0;
77          fclose (fp);
78          if (!strcmp (cpurev, "BCM4710 V0.0")) // BCM4702, BCM4710 (old 125 MHz)
79            return 0;
80          if (!strcmp (cpurev, "BCM3302 V0.6")) // BCM4704
81            return 6;
82          if (!strcmp (cpurev, "BCM3302 V0.7")) // BCM4712, BCM5365
83            return 7;
84          if (!strcmp (cpurev, "BCM3302 V0.8")) // BCM5350, BCM5352
85            return 8;
86          if (!strcmp (cpurev, "BCM3302 V2.9")) // BCM5354
87            return 29;
88          return -1;
89        }
90    }
91  fclose (fp);
92  return -1;
93}
94
95int
96cpu_plltype (void)
97{
98  int cpurev = getcpurev ();
99  int cputype = check_hw_type ();
100
101          if (cpurev == 0)      // BCM4702, BCM4710 (old 125 MHz)
102            return 0;
103          if (cpurev == 6)      // BCM4704
104            return 0;
105          if (cpurev == 7 && cputype == BCM5365_CHIP) // BCM5365 only supports fixed 200 MHz
106            return 0;     
107          if (cpurev == 7 && cputype != BCM5365_CHIP) // BCM4712
108            return 4;
109          if (cpurev == 8 && cputype == BCM5350_CHIP) // BCM5350
110            return 3;
111          if (cpurev == 8 && cputype != BCM5350_CHIP) // BCM5352
112            return 7;
113          if (cpurev == 29) // BCM5354, only supports fixed 240 MHz
114            return 0;
115          if (cputype == BCM4705_BCM5397_EWC_CHIP) // BCM4705
116            return 0; // could use table 2
117
118  return 0;
119}
120
121int
122startswith (char *source, char *cmp)
123{
124return !strncmp(source,cmp,strlen(cmp));
125/*  int i;
126  if (cmp == NULL)
127    return 0;
128  if (source == NULL)
129    return 0;
130  int slen = strlen (source);
131  int clen = strlen (cmp);
132  if (clen > slen)
133    return 0;
134
135  for (i = 0; i < clen; i++)
136    if (source[i] != cmp[i])
137      return 0;
138  return 1;*/
139}
140
141int
142count_occurences (char *source, int cmp)
143{
144   int i, cnt = 0;
145   int len = strlen (source);
146
147   for (i = 0; i < len; i++)
148       {
149       if (source[i] == cmp)
150          cnt++;
151       }
152   return cnt;
153}
154
155int
156pos_nthoccurence (char *source, int cmp, int which)
157{
158   int i, cnt = 0;
159   int len = strlen (source);
160
161   for (i=0; i < len; i++)
162           {
163                if (source[i] == cmp)
164          cnt++;
165                if (cnt == which)
166          return i;
167       }
168   return -1;
169}
170
171char *
172substring (int start, int stop, const char *src, char *dst)
173{
174   int count = stop - start;
175
176   sprintf(dst, "%.*s", count, src + start);
177
178   return dst;
179}
180
181void
182setRouter (char *name)
183{
184#ifdef HAVE_POWERNOC_WORT54G
185  nvram_set (NVROUTER, "WORT54G");
186#elif HAVE_POWERNOC_WOAP54G
187  nvram_set (NVROUTER, "WOAP54G");
188#elif HAVE_OMNI
189  nvram_set (NVROUTER, "Omni Wifi Router");
190#elif HAVE_MAKSAT
191  nvram_set (NVROUTER, "MAKSAT");
192#else
193  if (name)
194    nvram_set (NVROUTER, name);
195#endif
196}
197
198char *
199getRouter ()
200{
201  char *n = nvram_get (NVROUTER);
202  return n != NULL ? n : "Unknown Model";
203}
204
205
206
207int
208internal_getRouterBrand ()
209{
210
211#ifdef HAVE_RB500
212  setRouter ("Mikrotik RB500");
213  return ROUTER_BOARD_500;
214#elif HAVE_GEMTEK
215  setRouter ("SuperGerry");
216  return ROUTER_SUPERGERRY;
217#elif HAVE_GATEWORX
218  char *filename = "/sys/devices/platform/IXP4XX-I2C.0/i2c-adapter:i2c-0/0-0051/eeprom";        /* bank2=0x100 */
219  FILE *file = fopen (filename, "r");
220  if (file) //new detection scheme
221    {
222    fseek(file,32,SEEK_SET);
223    char gwid[7];
224    gwid[6]=0;
225    int ret = fread(gwid,6,1,file);
226    if (ret<1){
227        fclose(file);
228        goto old_way;
229        }
230    fclose(file);
231    if (!strcmp(gwid,"GW2347"))
232        {
233        setRouter ("Avila GW2347");
234        return ROUTER_BOARD_GATEWORX_SWAP;
235        }
236    if (!strcmp(gwid,"GW2348"))
237        {
238        setRouter ("Avila GW2348-4/2");
239        return ROUTER_BOARD_GATEWORX;
240        }
241    if (!strcmp(gwid,"GW2345"))
242        {
243        setRouter ("Avila GW2347");
244        return ROUTER_BOARD_GATEWORX_GW2345;
245        }
246    }
247  old_way:;
248  struct mii_ioctl_data *data;
249  struct ifreq iwr;
250  int s = socket (AF_INET, SOCK_DGRAM, 0);
251  if (s < 0)
252    {
253      fprintf (stderr, "socket(SOCK_DRAGM)\n");
254      setRouter ("Avila Gateworks");
255      return ROUTER_BOARD_GATEWORX;
256    }
257  (void) strncpy (iwr.ifr_name, "ixp0", sizeof ("ixp0"));
258  data = (struct mii_ioctl_data *) &iwr.ifr_data;
259  data->phy_id = 1;
260#define IX_ETH_ACC_MII_PHY_ID1_REG  0x2 /* PHY identifier 1 Register */
261#define IX_ETH_ACC_MII_PHY_ID2_REG  0x3 /* PHY identifier 2 Register */
262  data->reg_num = IX_ETH_ACC_MII_PHY_ID1_REG;
263  ioctl (s, SIOCGMIIREG, &iwr);
264  data->phy_id = 1;
265  data->reg_num = IX_ETH_ACC_MII_PHY_ID1_REG;
266  ioctl (s, SIOCGMIIREG, &iwr);
267  int reg1 = data->val_out;
268  data->phy_id = 1;
269  data->reg_num = IX_ETH_ACC_MII_PHY_ID2_REG;
270  ioctl (s, SIOCGMIIREG, &iwr);
271  int reg2 = data->val_out;
272  close (s);
273  fprintf (stderr, "phy id %X:%X\n", reg1, reg2);
274  if (reg1 == 0x2000 && reg2 == 0x5c90)
275    {
276      setRouter ("Avila GW2347");
277      return ROUTER_BOARD_GATEWORX_SWAP;
278    }
279  else if (reg1 == 0x13 && reg2 == 0x7a11)
280    {
281      setRouter ("Avila GW2348-4/2");
282      return ROUTER_BOARD_GATEWORX;
283    }
284  else if (reg1 == 0x22 && reg2 == 0x1450)      //kendin switch
285    {
286      setRouter ("Avila GW2345");
287      return ROUTER_BOARD_GATEWORX_GW2345;
288    }
289  else
290    {
291      setRouter ("Unknown");
292      return ROUTER_BOARD_GATEWORX;
293    }
294#elif HAVE_X86
295  setRouter ("Generic X86");
296  return ROUTER_BOARD_X86;
297#elif HAVE_XSCALE
298  setRouter ("NewMedia Dual A/B/G");
299  return ROUTER_BOARD_XSCALE;
300#elif HAVE_MAGICBOX
301  setRouter ("MagicBox");
302  return ROUTER_BOARD_MAGICBOX;
303#elif HAVE_WRK54G
304  setRouter ("Linksys WRK54G v3");
305  return ROUTER_BOARD_FONERA;
306#elif HAVE_MR3202A
307  setRouter ("MR3202A");
308  return ROUTER_BOARD_FONERA;
309#elif HAVE_AR430W
310  setRouter ("Airlink-101 AR430W");
311  return ROUTER_BOARD_FONERA;
312#elif HAVE_DIR300
313  setRouter ("D-Link DIR-300");
314  return ROUTER_BOARD_FONERA;
315#elif HAVE_FONERA
316  struct mii_ioctl_data *data;
317  struct ifreq iwr;
318  int s = socket (AF_INET, SOCK_DGRAM, 0);
319  if (s < 0)
320    {
321      fprintf (stderr, "socket(SOCK_DRAGM)\n");
322      setRouter ("Fonera 2100/2200");
323      return ROUTER_BOARD_FONERA;
324    }
325  (void) strncpy (iwr.ifr_name, "eth0", sizeof ("eth0"));
326  data = (struct mii_ioctl_data *) &iwr.ifr_data;
327  data->phy_id = 0x1f;
328  data->reg_num = 0x1;
329  ioctl (s, SIOCGMIIREG, &iwr);
330  close (s);
331  if (data->val_out & 0xffff != 0xffff) // marvell phy
332    {
333      setRouter ("Fonera+");
334      return ROUTER_BOARD_FONERA2200;
335    }
336  else
337    {
338      setRouter ("Fonera 2100/2200");
339      return ROUTER_BOARD_FONERA;
340    }
341#elif HAVE_MERAKI
342  setRouter ("Meraki Mini");
343  return ROUTER_BOARD_MERAKI;
344#elif HAVE_LS2
345  setRouter ("Ubiquiti Litestation 2");
346  return ROUTER_BOARD_LS2;
347#elif HAVE_LS5
348  setRouter ("Ubiquiti Litestation 5");
349  return ROUTER_BOARD_LS2;
350#elif HAVE_WHRAG108
351  setRouter ("Buffalo WHR-HP-AG108");
352  return ROUTER_BOARD_WHRAG108;
353#elif HAVE_PB42
354  setRouter ("Atheros PB42");
355  return ROUTER_BOARD_PB42;
356#elif HAVE_TW6600
357  setRouter ("TW6600");
358  return ROUTER_BOARD_TW6600;
359#elif HAVE_CA8
360  setRouter ("Wistron CA8-4");
361  return ROUTER_BOARD_CA8;
362#else
363
364  uint boardnum = strtoul (nvram_safe_get ("boardnum"), NULL, 0);
365
366  if (boardnum == 42 && nvram_match ("boardtype", "bcm94710ap"))
367    {
368      cprintf ("router is buffalo\n");
369      setRouter ("Buffalo WBR-G54 / WLA-G54");
370      return ROUTER_BUFFALO_WBR54G;
371    }
372#ifndef HAVE_BUFFALO
373  if (nvram_match ("boardnum", "mn700") &&
374      nvram_match ("boardtype", "bcm94710ap"))
375    {
376      cprintf ("router is Microsoft MN-700\n");
377      setRouter ("Microsoft MN-700");
378      return ROUTER_MICROSOFT_MN700;
379    }
380
381  if (nvram_match ("boardnum", "asusX") &&
382      nvram_match ("boardtype", "bcm94710dev"))
383    {
384      cprintf ("router is Asus WL300g / WL500g\n");
385      setRouter ("Asus WL-300g / WL-500g");
386      return ROUTER_ASUS_WL500G;
387    }
388
389  if (boardnum == 44 && nvram_match ("boardtype", "bcm94710ap"))
390    {
391      cprintf ("router is Dell TrueMobile 2300\n");
392      setRouter ("Dell TrueMobile 2300");
393      return ROUTER_DELL_TRUEMOBILE_2300;
394    }
395#endif
396
397  if (boardnum == 100 && nvram_match ("boardtype", "bcm94710dev"))
398    {
399      cprintf ("router is buffalo\n");
400      setRouter ("Buffalo WLA-G54C");
401      return ROUTER_BUFFALO_WLAG54C;
402    }
403
404#ifndef HAVE_BUFFALO
405  if (boardnum == 45 && nvram_match ("boardtype", "bcm95365r"))
406    {
407      cprintf ("router is Asus WL-500GD\n");
408      setRouter ("Asus WL-500g Deluxe");
409      return ROUTER_ASUS_WL500GD;
410    }
411   
412  if (boardnum == 45 && nvram_match ("boardtype", "0x0472")
413      && nvram_match ("boardrev", "0x23") && nvram_match ("parkid", "1"))
414    {
415      cprintf ("router is Asus WL-500W\n");
416      setRouter ("Asus WL-500W");
417      return ROUTER_ASUS_WL500W;
418    }
419   
420  if (boardnum == 45 && nvram_match ("boardtype", "0x467"))
421    {
422      cprintf ("router is Asus WL-550gE\n");
423      setRouter ("Asus WL-550gE");
424      return ROUTER_ASUS_WL550GE;
425    }
426#endif
427  if (nvram_match ("boardnum", "00") &&
428      nvram_match ("boardtype", "0x0101") && nvram_match ("boardrev", "0x10"))
429    {
430      cprintf ("router is Buffalo wbr2\n");
431      setRouter ("Buffalo WBR2-G54 / WBR2-G54S");
432      return ROUTER_BUFFALO_WBR2G54S;
433    }
434
435  if (boardnum == 2 &&
436      nvram_match ("boardtype", "0x0101") && nvram_match ("boardrev", "0x10"))
437    {
438      cprintf ("router is buffalo wla2-g54c\n");
439      setRouter ("Buffalo WLA2-G54C / WLI3-TX1-G54");
440      return ROUTER_BUFFALO_WLA2G54C;
441    }
442  if (boardnum == 0 && nvram_match ("melco_id", "29090")
443      && nvram_match ("boardflags", "0x0010")
444      && nvram_match ("boardrev", "0x10"))
445    {
446      cprintf ("router is Buffalo WLAH-G54\n");
447      setRouter ("Buffalo WLAH-G54");
448      return ROUTER_BUFFALO_WLAH_G54;
449
450    }
451  if (boardnum == 0 && nvram_match ("melco_id", "31070")
452      && nvram_match ("boardflags", "0x2288")
453      && nvram_match ("boardrev", "0x10"))
454    {
455      cprintf ("router is Buffalo WAPM-HP-AM54G54\n");
456      setRouter ("Buffalo WAPM-HP-AM54G54");
457      return ROUTER_BUFFALO_WAPM_HP_AM54G54;
458    }
459  if (nvram_match ("boardnum", "00") && nvram_match ("boardrev", "0x11")
460      && nvram_match ("boardtype", "0x048e")
461      && nvram_match ("melco_id", "32093"))
462    {
463      cprintf ("router is Buffalo WHR-G125\n");
464      setRouter ("Buffalo WHR-G125");
465      return ROUTER_BUFFALO_WHRG54S;
466    }
467
468  if (nvram_match ("boardnum", "00") &&
469      nvram_match ("boardrev", "0x13") && nvram_match ("boardtype", "0x467"))
470    {
471      if (nvram_match ("boardflags", "0x1658")
472       || nvram_match ("boardflags", "0x2658")
473       || nvram_match ("boardflags", "0x3658"))
474        {
475          cprintf ("router is Buffalo WLI-TX4-G54HP\n");
476          setRouter ("Buffalo WLI-TX4-G54HP");
477          return ROUTER_BUFFALO_WLI_TX4_G54HP;
478        }
479      if (!nvram_match ("buffalo_hp", "1") && nvram_match ("boardflags", "0x2758"))
480        {
481          cprintf ("router is Buffalo WHR-G54S\n");
482          setRouter ("Buffalo WHR-G54S");
483          return ROUTER_BUFFALO_WHRG54S;
484        }
485      if (nvram_match ("buffalo_hp", "1") || nvram_match ("boardflags", "0x1758"))
486        {
487#ifndef HAVE_BUFFALO           
488          cprintf ("router is Buffalo WHR-HP-G54\n");
489          setRouter ("Buffalo WHR-HP-G54");
490#else
491          cprintf ("router is Buffalo WHR-HP-G54DD\n");
492#ifdef BUFFALO_JP
493          setRouter ("Buffalo AS-A100");
494#else
495          setRouter ("Buffalo WHR-HP-G54DD");
496#endif
497#endif
498          return ROUTER_BUFFALO_WHRG54S;
499        }
500    }
501
502  if (nvram_match ("boardnum", "00") &&
503      nvram_match ("boardrev", "0x10") && nvram_match ("boardtype", "0x470"))
504    {
505      cprintf ("router is Buffalo WHR-AM54G54\n");
506      setRouter ("Buffalo WHR-AM54G54");
507      return ROUTER_BUFFALO_WHRAM54G54;
508    }
509
510
511  if (boardnum == 42 && nvram_match ("boardtype", "0x042f"))
512    {
513      uint melco_id = strtoul (nvram_safe_get ("melco_id"), NULL, 0);
514
515      if (nvram_match ("product_name", "WZR-RS-G54") || melco_id == 30083)
516        {
517          cprintf ("router is Buffalo WZR-RS-G54\n");
518          setRouter ("Buffalo WZR-RS-G54");
519          return ROUTER_BUFFALO_WZRRSG54;
520        }
521      if (nvram_match ("product_name", "WZR-HP-G54") || melco_id == 30026)
522        {
523          cprintf ("router is Buffalo WZR-HP-G54\n");
524          setRouter ("Buffalo WZR-HP-G54");
525          return ROUTER_BUFFALO_WZRRSG54;
526        }
527      if (nvram_match ("product_name", "WZR-G54") || melco_id == 30061)
528        {
529          cprintf ("router is Buffalo WZR-G54\n");
530          setRouter ("Buffalo WZR-G54");
531          return ROUTER_BUFFALO_WZRRSG54;
532        }
533      if (nvram_match ("melco_id", "290441dd"))
534        {
535          cprintf ("router is Buffalo WHR2-A54G54\n");
536          setRouter ("Buffalo WHR2-A54G54");
537          return ROUTER_BUFFALO_WZRRSG54;
538        }
539      if (nvram_match ("product_name", "WHR3-AG54")
540          || nvram_match ("product_name", "WHR3-B11") || melco_id == 29130)
541        {
542          cprintf ("router is Buffalo WHR3-AG54\n");
543          setRouter ("Buffalo WHR3-AG54");
544          return ROUTER_BUFFALO_WZRRSG54;
545        }
546      if (nvram_match ("product_name", "WVR-G54-NF") || melco_id == 28100)
547        {
548          cprintf ("router is Buffalo WVR-G54-NF\n");
549          setRouter ("Buffalo WVR-G54-NF");
550          return ROUTER_BUFFALO_WZRRSG54;
551        }
552      if (melco_id > 0)         //e.g. 29115
553        {
554          cprintf ("router is Buffalo WZR series\n");
555          setRouter ("Buffalo WZR series");
556          return ROUTER_BUFFALO_WZRRSG54;
557        }
558    }
559
560#ifndef HAVE_BUFFALO
561  if (boardnum == 42 &&
562      nvram_match ("boardtype", "0x042f") && nvram_match ("boardrev", "0x10"))
563//      nvram_match ("boardflags","0x0018"))
564    {
565      cprintf ("router is Linksys WRTSL54GS\n");
566      setRouter ("Linksys WRTSL54GS");
567      return ROUTER_WRTSL54GS;
568    }
569
570  if (boardnum == 42 && nvram_match ("boardtype", "0x0101")
571      && nvram_match ("boardrev", "0x10") && nvram_match ("boot_ver", "v3.6"))
572    {
573      cprintf ("router is Linksys WRT54G3G\n");
574      setRouter ("Linksys WRT54G3G");
575      return ROUTER_WRT54G3G;
576    }
577
578  if (boardnum == 45 &&
579      nvram_match ("boardtype", "0x042f") && nvram_match ("boardrev", "0x10"))
580    {
581      cprintf ("router is Asus WL-500g Premium\n");
582      setRouter ("Asus WL-500g Premium");
583      return ROUTER_ASUS_WL500G_PRE;
584    }
585
586
587  char *et0 = nvram_safe_get ("et0macaddr");
588
589  if (boardnum == 100 && nvram_match ("boardtype", "bcm94710r4"))
590    {
591      if (startswith (et0, "00:11:50"))
592        {
593          cprintf ("router is Belkin F5D7130 / F5D7330\n");
594          setRouter ("Belkin F5D7130 / F5D7330");
595          return ROUTER_RT210W;
596        }
597      if (startswith (et0, "00:30:BD") || startswith (et0, "00:30:bd"))
598        {
599          cprintf ("router is Belkin F5D7230 v1000\n");
600          setRouter ("Belkin F5D7230-4 v1000");
601          return ROUTER_RT210W;
602        }
603      if (startswith (et0, "00:01:E3") ||
604          startswith (et0, "00:01:e3") || startswith (et0, "00:90:96"))
605        {
606          cprintf ("router is Siemens\n");
607          setRouter ("Siemens SE505 v1");
608          return ROUTER_RT210W;
609        }
610      else
611        {
612          cprintf ("router is Askey generic\n");
613          setRouter ("RT210W generic");
614          return ROUTER_RT210W;
615        }
616    }
617
618  if (nvram_match ("boardtype", "bcm94710r4") && nvram_match ("boardnum", ""))
619    {
620      cprintf ("router is Askey board RT2100W\n");
621      setRouter ("Askey board RT2100W-D65)");
622      return ROUTER_BRCM4702_GENERIC;
623    }
624
625  if (nvram_match ("boardtype", "0x0100") && nvram_match ("boardnum", ""))
626    {
627      cprintf ("router is Askey board RT2206D\n");
628      setRouter ("Askey board RT2206D-D56");
629      return ROUTER_BRCM4702_GENERIC;
630    }
631
632  if (nvram_match ("boardtype", "0x0101"))
633    {
634      if (startswith (et0, "00:11:50") ||
635          startswith (et0, "00:30:BD") || startswith (et0, "00:30:bd"))
636        {
637      if (nvram_match ("Belkin_ver", "2000"))
638      {
639          cprintf ("router is Belkin F5D7230-4 v2000\n");
640          setRouter ("Belkin F5D7230-4 v2000");
641          return ROUTER_BELKIN_F5D7230_V2000;         
642      }
643      else
644      {     
645          cprintf ("router is Belkin F5D7230-4 v1444\n");
646          setRouter ("Belkin F5D7230-4 v1444");
647          return ROUTER_RT480W;
648      }
649        }
650      if (startswith (et0, "00:01:E3") ||
651          startswith (et0, "00:01:e3") || startswith (et0, "00:90:96"))
652        {
653          cprintf ("router is Siemens / Askey\n");
654          setRouter ("Siemens SE505 v2");
655          return ROUTER_RT480W;
656        }
657    }
658
659  if (nvram_match ("boardtype", "0x456") && nvram_match ("hw_model", "F5D7231-4"))
660    {
661          cprintf ("router is Belkin F5D7231-4 v1212UK\n");
662          setRouter ("Belkin F5D7231-4 v1212UK");
663          return ROUTER_BELKIN_F5D7231;
664    }
665   
666  if (nvram_match ("boardtype", "0x467"))
667    {
668      if (startswith (et0, "00:11:50") ||
669          startswith (et0, "00:30:BD") || startswith (et0, "00:30:bd"))
670        {
671          cprintf ("router is Belkin F5D7231-4 v2000\n");
672          setRouter ("Belkin F5D7231-4 v2000");
673          return ROUTER_BELKIN_F5D7231;
674        }
675    }
676#endif
677  if (boardnum == 2 && nvram_match ("boardtype", "bcm94710dev") && nvram_match ("melco_id", "29016"))   //Buffalo WLI2-TX1-G54)
678    {
679      cprintf ("router is Buffalo WLI2-TX1-G54\n");
680      setRouter ("Buffalo WLI2-TX1-G54");
681      return ROUTER_BUFFALO_WLI2_TX1_G54;
682    }
683#ifndef HAVE_BUFFALO
684
685  char *gemtek = nvram_safe_get ("GemtekPmonVer");
686  uint gemteknum = strtoul (gemtek, NULL, 0);
687 
688  if (boardnum == 2 && gemteknum == 10 &&
689     (startswith (et0, "00:0C:E5") ||
690          startswith (et0, "00:0c:e5") ||
691          startswith (et0, "00:0C:10") ||
692          startswith (et0, "00:0c:10") ||
693          startswith (et0, "00:0C:11") ||
694          startswith (et0, "00:0c:11")))
695        {
696          cprintf ("router Motorola WE800G v1\n");
697          setRouter ("Motorola WE800G v1");
698          return ROUTER_MOTOROLA_WE800G;
699        }
700
701  if (boardnum == 2 && (startswith (gemtek, "RC") || gemteknum == 1 || gemteknum == 10))
702    {
703          cprintf ("router is Linksys wap54g v1.x\n");
704          setRouter ("Linksys WAP54G v1.x");
705          return ROUTER_WAP54G_V1;
706    }
707       
708  if (boardnum == 2 && gemteknum == 1)
709    {
710      cprintf ("router is Sitecom wl-105b\n");
711      setRouter ("Sitecom WL-105(b)");
712      return ROUTER_SITECOM_WL105B;
713    }
714
715  if (boardnum == 2 && gemteknum == 7 && nvram_match ("boardtype", "bcm94710dev"))
716    {
717      cprintf ("router is Sitecom wl-111\n");
718      setRouter ("Sitecom WL-111");
719      return ROUTER_SITECOM_WL111;
720    }
721
722  if (gemteknum == 9)   //Must be Motorola wr850g v1 or we800g v1 or Linksys wrt55ag v1
723    {
724      if (startswith (et0, "00:0C:E5") ||
725          startswith (et0, "00:0c:e5") ||
726          startswith (et0, "00:0C:10") ||
727          startswith (et0, "00:0c:10") ||
728          startswith (et0, "00:0C:11") ||
729          startswith (et0, "00:0c:11") ||
730          startswith (et0, "00:11:22") ||
731          startswith (et0, "00:0C:90") ||
732          startswith (et0, "00:0c:90"))
733        {
734          if (!strlen (nvram_safe_get ("phyid_num")))
735            {
736              eval ("insmod", "switch-core");   //get phy type
737              eval ("insmod", "switch-robo");
738              eval ("rmmod", "switch-robo");
739              eval ("rmmod", "switch-core");
740              nvram_set ("boardnum", "2");
741              nvram_set ("boardtype", "bcm94710dev");
742            }
743          if (nvram_match ("phyid_num", "0x00000000"))
744            {
745              cprintf ("router Motorola WE800G v1\n");
746              setRouter ("Motorola WE800G v1");
747              return ROUTER_MOTOROLA_WE800G;
748            }
749          else                  //phyid_num == 0xffffffff
750            {
751              cprintf ("router Motorola WR850G v1\n");
752              setRouter ("Motorola WR850G v1");
753              return ROUTER_MOTOROLA_V1;
754            }
755        }
756      else
757        {
758          cprintf ("router is linksys WRT55AG\n");
759          setRouter ("Linksys WRT55AG v1");
760          return ROUTER_LINKSYS_WRT55AG;
761        }
762    }
763#endif
764  if (boardnum == 0 && nvram_match ("boardtype", "0x478")
765      && nvram_match ("cardbus", "0") && nvram_match ("boardrev", "0x10")
766      && nvram_match ("boardflags", "0x110")
767      && nvram_match ("melco_id", "32027"))
768    {
769      setRouter ("Buffalo WZR-G144NH");
770      return ROUTER_BUFFALO_WZRG144NH;
771    }
772
773
774  if (boardnum == 20060330 && nvram_match ("boardtype", "0x0472"))
775    {
776      setRouter ("Buffalo WZR-G300N");
777      return ROUTER_BUFFALO_WZRG300N;
778    }
779#ifndef HAVE_BUFFALO
780
781  if (boardnum == 8 &&
782      nvram_match ("boardtype", "0x0472") && nvram_match ("cardbus", "1"))
783    {
784      setRouter ("Netgear WNR834B");
785      return ROUTER_NETGEAR_WNR834B;
786    }
787
788  if (boardnum == 42 &&
789      nvram_match ("boardtype", "0x0472") && nvram_match ("cardbus", "1"))
790    {
791      if (nvram_match ("boot_hw_model", "WRT150N"))
792        {
793          setRouter ("Linksys WRT150N");
794          return ROUTER_WRT150N;
795        }
796      else
797        {
798          setRouter ("Linksys WRT300N v1");
799          return ROUTER_WRT300N;
800        }
801    }
802
803  if (boardnum == 42 &&
804      nvram_match ("boardtype", "0x478") && nvram_match ("cardbus", "1"))
805    {
806      cprintf ("router is Linksys WRT350N\n");
807      setRouter ("Linksys WRT350N");
808      return ROUTER_WRT350N;
809    }
810
811  if (nvram_match("boardnum","20070615") &&
812      nvram_match ("boardtype", "0x478") && nvram_match ("cardbus", "0"))
813    {
814      cprintf ("router is Linksys WRT600N\n");
815      setRouter ("Linksys WRT600N");
816      return ROUTER_WRT600N;
817    }
818
819  if (boardnum == 42 && nvram_match ("boardtype", "bcm94710dev"))
820    {
821      cprintf ("router is Linksys WRT54G v1.x\n");
822      setRouter ("Linksys WRT54G v1.x");
823      return ROUTER_WRT54G1X;
824    }
825
826  if (boardnum == 1 && nvram_match ("boardtype", "0x0446"))
827    {
828      cprintf ("router is U.S. Robotics USR5430\n");
829      setRouter ("U.S.Robotics USR5430");
830      return ROUTER_USR_5430;
831    }
832   
833  if (boardnum == 1 && nvram_match ("boardtype", "0x456"))
834    {
835      cprintf ("router is Netgear WG602 v3\n");     
836      setRouter ("Netgear WG602 v3");
837      return ROUTER_NETGEAR_WG602_V3;
838    }
839
840  if (boardnum == 10496 && nvram_match ("boardtype", "0x456"))
841    {
842      setRouter ("U.S.Robotics USR5461");
843      return ROUTER_USR_5461;
844    }
845
846  if (boardnum == 1024 && nvram_match ("boardtype", "0x0446"))
847    {
848      char *cfe = nvram_safe_get ("cfe_version");
849      if (strstr (cfe, "iewsonic"))
850        {
851          cprintf ("router is Viewsonic WAPBR-100\n");
852          setRouter ("Viewsonic WAPBR-100");
853          return ROUTER_VIEWSONIC_WAPBR_100;
854        }
855      else
856        {
857          cprintf ("router is Linksys WAP54G v2\n");
858          setRouter ("Linksys WAP54G v2");
859          return ROUTER_WAP54G_V2;
860        }
861    }
862
863  if (nvram_invmatch ("CFEver", ""))
864    {
865      char *cfe = nvram_safe_get ("CFEver");
866      if (!strncmp (cfe, "MotoWR", 6))
867        {
868          cprintf ("router is motorola\n");
869          setRouter ("Motorola WR850G v2/v3");
870          return ROUTER_MOTOROLA;
871        }
872    }
873
874  if (boardnum == 44 &&
875      (nvram_match ("boardtype", "0x0101")
876       || nvram_match ("boardtype", "0x0101\r")))
877    {
878      char *cfe = nvram_safe_get ("CFEver");
879      if (!strncmp (cfe, "GW_WR110G", 9))
880        {
881          cprintf ("router is Sparklan WX-6615GT\n");
882          setRouter ("Sparklan WX-6615GT");
883          return ROUTER_DELL_TRUEMOBILE_2300_V2;
884        }
885      else
886        {
887          cprintf ("router is Dell TrueMobile 2300 v2\n");
888          setRouter ("Dell TrueMobile 2300 v2");
889          return ROUTER_DELL_TRUEMOBILE_2300_V2;
890        }
891    }
892#endif
893  if (nvram_match ("boardtype", "bcm94710ap"))
894    {
895      cprintf ("router is Buffalo old 4710\n");
896      setRouter ("Buffalo WBR-B11");
897      return ROUTER_BUFFALO_WBR54G;
898    }
899#ifndef HAVE_BUFFALO
900  if (nvram_match ("boardtype", "0x048e") &&
901      nvram_match ("boardrev", "0x35") &&
902      nvram_match ("sdram_init", "0x000b"))
903    {
904      cprintf ("router is D-Link DIR-320\n");
905      setRouter ("D-Link DIR-320");
906      //apply some fixes
907      if (nvram_get("vlan2ports")!=NULL)
908      {
909        nvram_unset("vlan2ports");
910        nvram_unset("vlan2hwname");
911      }
912      return ROUTER_DLINK_DIR320;
913    }
914  if (boardnum == 42 &&
915      nvram_match ("boardtype", "0x048e") && nvram_match ("boardrev", "0x10"))
916    {
917      cprintf ("router is wrt54g v8\n");
918      setRouter ("Linksys WRT54Gv8 / GSv7");
919      return ROUTER_WRT54G_V8;
920    }
921
922  if (boardnum == 45 &&
923      nvram_match ("boardtype", "0x456"))
924    {
925      cprintf ("router is Asus WL-520G\n");
926      setRouter ("Asus WL-520G");
927      return ROUTER_ASUS_WL520G;
928    }   
929   
930  if (boardnum == 45 &&
931      nvram_match ("boardtype", "0x48E") && nvram_match ("boardrev", "0x10"))
932    {
933      cprintf ("router is Asus WL-520GU/GC\n");
934      setRouter ("Asus WL-520GU/GC");
935      return ROUTER_ASUS_WL520GUGC;
936    }       
937
938  if (boardnum == 56 &&
939      nvram_match ("boardtype", "0x456") && nvram_match ("boardrev", "0x10"))
940    {
941      cprintf ("router is wtr54gs\n");
942      setRouter ("Linksys WTR54GS");
943      return ROUTER_LINKSYS_WTR54GS;
944    }
945
946  if (nvram_match("boardnum", "WAP54GV3_8M_0614") && (nvram_match ("boardtype", "0x0467") || nvram_match ("boardtype", "0x467"))
947    && nvram_match ("WAPver", "3"))
948    {
949      cprintf ("router is WAP54G v3.x\n");
950      setRouter ("Linksys WAP54G v3.x");
951      return ROUTER_WAP54G_V3;
952    }
953   
954  setRouter ("Linksys WRT54G/GL/GS");
955  cprintf ("router is wrt54g\n");
956  return ROUTER_WRT54G;
957#else
958  eval ("event", "3", "1", "15");
959  return 0;
960#endif
961#endif
962
963}
964
965int
966has_mimo (char *prefix)
967{
968  if (nvram_nmatch ("n","%s_phytypes", prefix))
969    return 1;
970  return 0;
971}
972
973static int router_type = -1;
974int
975getRouterBrand ()
976{
977  if (router_type == -1)
978    router_type = internal_getRouterBrand ();
979  return router_type;
980}
981
982
983int
984diag_led_4702 (int type, int act)
985{
986
987#if defined(HAVE_GEMTEK) || defined(HAVE_RB500) || defined(HAVE_XSCALE) || defined(HAVE_MAGICBOX) || defined(HAVE_FONERA) || defined(HAVE_MERAKI) || defined(HAVE_LS2) || defined(HAVE_WHRAG108) || defined(HAVE_X86) || defined(HAVE_CA8) || defined(HAVE_TW6600) || defined(HAVE_PB42) || defined(HAVE_LS5) || defined(HAVE_FONERA)
988  return 0;
989#else
990  if (act == START_LED)
991    {
992      switch (type)
993        {
994        case DMZ:
995          system2 ("echo 1 > /proc/sys/diag");
996          break;
997        }
998    }
999  else
1000    {
1001      switch (type)
1002        {
1003        case DMZ:
1004          system2 ("echo 0 > /proc/sys/diag");
1005          break;
1006        }
1007    }
1008  return 0;
1009#endif
1010}
1011
1012int
1013C_led_4702 (int i)
1014{
1015#if defined(HAVE_GEMTEK) || defined(HAVE_RB500) || defined(HAVE_XSCALE) || defined(HAVE_MAGICBOX) || defined(HAVE_FONERA) || defined(HAVE_MERAKI) || defined(HAVE_LS2) || defined(HAVE_WHRAG108) || defined(HAVE_X86) || defined(HAVE_CA8) || defined(HAVE_TW6600) || defined(HAVE_PB42) || defined(HAVE_LS5)
1016  return 0;
1017#else
1018  FILE *fp;
1019  char string[10];
1020  int flg;
1021
1022  memset (string, 0, 10);
1023  /* get diag before set */
1024  if ((fp = fopen ("/proc/sys/diag", "r")))
1025    {
1026      fgets (string, sizeof (string), fp);
1027      fclose (fp);
1028    }
1029  else
1030    perror ("/proc/sys/diag");
1031
1032  if (i)
1033    flg = atoi (string) | 0x10;
1034  else
1035    flg = atoi (string) & 0xef;
1036
1037  memset (string, 0, 10);
1038  sprintf (string, "%d", flg);
1039  if ((fp = fopen ("/proc/sys/diag", "w")))
1040    {
1041      fputs (string, fp);
1042      fclose (fp);
1043    }
1044  else
1045    perror ("/proc/sys/diag");
1046
1047  return 0;
1048#endif
1049}
1050
1051unsigned int
1052read_gpio (char *device)
1053{
1054  FILE *fp;
1055  unsigned int val;
1056
1057  if ((fp = fopen (device, "r")))
1058    {
1059      fread (&val, 4, 1, fp);
1060      fclose (fp);
1061      //fprintf(stderr, "----- gpio %s = [%X]\n",device,val);
1062      return val;
1063    }
1064  else
1065    {
1066      perror (device);
1067      return 0;
1068    }
1069}
1070
1071unsigned int
1072write_gpio (char *device, unsigned int val)
1073{
1074  FILE *fp;
1075
1076  if ((fp = fopen (device, "w")))
1077    {
1078      fwrite (&val, 4, 1, fp);
1079      fclose (fp);
1080      //fprintf(stderr, "----- set gpio %s = [%X]\n",device,val);
1081      return 1;
1082    }
1083  else
1084    {
1085      perror (device);
1086      return 0;
1087    }
1088}
1089
1090static char hw_error = 0;
1091int
1092diag_led_4704 (int type, int act)
1093{
1094#if defined(HAVE_GEMTEK) || defined(HAVE_RB500) || defined(HAVE_XSCALE) || defined(HAVE_MAGICBOX) || defined(HAVE_FONERA) || defined(HAVE_MERAKI)|| defined(HAVE_LS2) || defined(HAVE_WHRAG108) || defined(HAVE_X86) || defined(HAVE_CA8) || defined(HAVE_TW6600) || defined(HAVE_PB42) || defined(HAVE_LS5)
1095  return 0;
1096#else
1097  unsigned int control, in, outen, out;
1098
1099#ifdef BCM94712AGR
1100  /* The router will crash, if we load the code into broadcom demo board. */
1101  return 1;
1102#endif
1103  //int brand;
1104  control = read_gpio ("/dev/gpio/control");
1105  in = read_gpio ("/dev/gpio/in");
1106  out = read_gpio ("/dev/gpio/out");
1107  outen = read_gpio ("/dev/gpio/outen");
1108
1109  write_gpio ("/dev/gpio/outen", (outen & 0x7c) | 0x83);
1110  switch (type)
1111    {
1112    case DIAG:                  // GPIO 1
1113      if (hw_error)
1114        {
1115          write_gpio ("/dev/gpio/out", (out & 0x7c) | 0x00);
1116          return 1;
1117        }
1118
1119      if (act == STOP_LED)
1120        {                       // stop blinking
1121          write_gpio ("/dev/gpio/out", (out & 0x7c) | 0x83);
1122          //cprintf("tallest:=====( DIAG STOP_LED !!)=====\n");
1123        }
1124      else if (act == START_LED)
1125        {                       // start blinking
1126          write_gpio ("/dev/gpio/out", (out & 0x7c) | 0x81);
1127          //cprintf("tallest:=====( DIAG START_LED !!)=====\n");
1128        }
1129      else if (act == MALFUNCTION_LED)
1130        {                       // start blinking
1131          write_gpio ("/dev/gpio/out", (out & 0x7c) | 0x00);
1132          hw_error = 1;
1133          //cprintf("tallest:=====( DIAG MALFUNCTION_LED !!)=====\n");
1134        }
1135      break;
1136
1137    }
1138  return 1;
1139#endif
1140}
1141
1142int
1143diag_led_4712 (int type, int act)
1144{
1145  unsigned int control, in, outen, out, ctr_mask, out_mask;
1146#if defined(HAVE_GEMTEK) || defined(HAVE_RB500) || defined(HAVE_XSCALE) || defined(HAVE_MAGICBOX) || defined(HAVE_FONERA)|| defined(HAVE_MERAKI) || defined(HAVE_LS2) || defined(HAVE_WHRAG108) || defined(HAVE_X86) || defined(HAVE_CA8) || defined(HAVE_TW6600) || defined(HAVE_PB42) || defined(HAVE_LS5)
1147  return 0;
1148#else
1149
1150
1151#ifdef BCM94712AGR
1152  /* The router will crash, if we load the code into broadcom demo board. */
1153  return 1;
1154#endif
1155  control = read_gpio ("/dev/gpio/control");
1156  in = read_gpio ("/dev/gpio/in");
1157  out = read_gpio ("/dev/gpio/out");
1158  outen = read_gpio ("/dev/gpio/outen");
1159
1160  ctr_mask = ~(1 << type);
1161  out_mask = (1 << type);
1162
1163  write_gpio ("/dev/gpio/control", control & ctr_mask);
1164  write_gpio ("/dev/gpio/outen", outen | out_mask);
1165
1166  if (act == STOP_LED)
1167    {                           // stop blinking
1168      //cprintf("%s: Stop GPIO %d\n", __FUNCTION__, type);
1169      write_gpio ("/dev/gpio/out", out | out_mask);
1170    }
1171  else if (act == START_LED)
1172    {                           // start blinking
1173      //cprintf("%s: Start GPIO %d\n", __FUNCTION__, type);
1174      write_gpio ("/dev/gpio/out", out & ctr_mask);
1175    }
1176
1177  return 1;
1178#endif
1179}
1180
1181int
1182C_led_4712 (int i)
1183{
1184  if (i == 1)
1185    return diag_led (DIAG, START_LED);
1186  else
1187    return diag_led (DIAG, STOP_LED);
1188}
1189
1190int
1191C_led (int i)
1192{
1193//show_hw_type(check_hw_type());
1194  int brand = getRouterBrand ();
1195 
1196  if (brand == ROUTER_WRT54G1X
1197      || brand == ROUTER_LINKSYS_WRT55AG)
1198    return C_led_4702 (i);
1199  else if (brand == ROUTER_WRT54G)
1200    return C_led_4712 (i);
1201  else
1202    return 0;
1203}
1204
1205int
1206diag_led (int type, int act)
1207{
1208  int brand = getRouterBrand ();
1209
1210  if (brand == ROUTER_WRT54G || brand == ROUTER_WRT54G3G)
1211    return diag_led_4712 (type, act);
1212  else if (brand == ROUTER_WRT54G1X || brand == ROUTER_LINKSYS_WRT55AG)
1213    return diag_led_4702 (type, act);
1214  else
1215    if ((brand == ROUTER_WRTSL54GS || brand == ROUTER_WRT350N
1216         || brand == ROUTER_BUFFALO_WZRG144NH) && type == DIAG)
1217    return diag_led_4704 (type, act);
1218  else
1219    {
1220      if (type == DMZ)
1221        {
1222          if (act == START_LED)
1223            return led_control (LED_DMZ, LED_ON);
1224          if (act == STOP_LED)
1225            return led_control (LED_DMZ, LED_OFF);
1226          return 1;
1227        }
1228    }
1229  return 0;
1230}
1231
1232int
1233led_control (int type, int act)
1234/* type: LED_POWER, LED_DIAG, LED_DMZ, LED_CONNECTED, LED_BRIDGE, LED_VPN, LED_SES, LED_SES2, LED_WLAN
1235 * act: LED_ON, LED_OFF, LED_FLASH */
1236{
1237#if defined(HAVE_GEMTEK) || defined(HAVE_RB500) || defined(HAVE_MAGICBOX) || defined(HAVE_MERAKI) || defined(HAVE_LS2) || defined(HAVE_X86) || defined(HAVE_CA8) || defined(HAVE_LS5)  && !defined(HAVE_DIR300)
1238  return 0;
1239#else
1240
1241#ifdef HAVE_GATEWORX
1242  int board = getRouterBrand ();
1243  char *gpio = "3";
1244  if (board == ROUTER_BOARD_GATEWORX_SWAP)
1245    gpio = "4";
1246#endif
1247  int use_gpio = 0x0f;
1248  int gpio_value;
1249  char val[4];
1250  char enable[16];
1251  char disable[16];
1252
1253  int power_gpio = 0x0f;
1254  int diag_gpio = 0x0f;
1255  int dmz_gpio = 0x0f;
1256  int connected_gpio = 0x0f;
1257  int bridge_gpio = 0x0f;
1258  int vpn_gpio = 0x0f;
1259  int ses_gpio = 0x0f;          //use for SES1 (Linksys), AOSS (Buffalo) ....
1260  int ses2_gpio = 0x0f;
1261  int wlan_gpio = 0x0f;         //use this only if wlan led is not controlled by hardware!
1262  int v1func = 0;
1263  switch (getRouterBrand ())    //gpio definitions here: 0xYZ, Y=0:normal, Y=1:inverted, Z:gpio number (f=disabled)
1264    {
1265#ifndef HAVE_BUFFALO
1266    case ROUTER_WRT54G:
1267    case ROUTER_WRT54G_V8:
1268      power_gpio = 0x01;
1269      dmz_gpio = 0x17;
1270      connected_gpio = 0x13;    //ses orange
1271      ses_gpio = 0x12;          //ses white
1272      ses2_gpio = 0x13;         //ses orange
1273      break;
1274    case ROUTER_WRT54G1X:
1275      connected_gpio = 0x13;
1276      v1func = 1;
1277      break;
1278    case ROUTER_WRT350N:
1279      connected_gpio = 0x13;
1280      power_gpio = 0x01;
1281      ses2_gpio = 0x13;         //ses orange                   
1282      break;
1283    case ROUTER_WRT600N:
1284      connected_gpio = 0x13;
1285//      power_gpio = 0x01;
1286      ses2_gpio = 0x18;         //ses orange                   
1287      break;
1288    case ROUTER_LINKSYS_WRT55AG:
1289      connected_gpio = 0x13;
1290      break;
1291#endif
1292    case ROUTER_BUFFALO_WBR54G:
1293      diag_gpio = 0x17;
1294      break;
1295    case ROUTER_BUFFALO_WBR2G54S:
1296      diag_gpio = 0x01;
1297      ses_gpio = 0x06;
1298      break;
1299    case ROUTER_BUFFALO_WLA2G54C:
1300      diag_gpio = 0x14;
1301      ses_gpio = 0x13;
1302      break;
1303    case ROUTER_BUFFALO_WLAH_G54:
1304      diag_gpio = 0x17;
1305      ses_gpio = 0x16;
1306      break;
1307    case ROUTER_BUFFALO_WAPM_HP_AM54G54:
1308      diag_gpio = 0x17;
1309      ses_gpio = 0x11;
1310      break;
1311    case ROUTER_BOARD_WHRAG108:
1312      diag_gpio = 0x17;
1313      bridge_gpio = 0x14;
1314      ses_gpio = 0x10;
1315      break;
1316#ifdef HAVE_DIR300
1317    case ROUTER_BOARD_FONERA:
1318      diag_gpio = 0x03;
1319      bridge_gpio = 0x04;
1320      ses_gpio = 0x01;
1321      break;
1322#endif
1323#ifdef HAVE_WRK54G
1324    case ROUTER_BOARD_FONERA:
1325      diag_gpio = 0x17;
1326      dmz_gpio = 0x05;
1327      break;
1328#endif
1329    case ROUTER_BOARD_TW6600:
1330      diag_gpio = 0x17;
1331      bridge_gpio = 0x14;
1332      ses_gpio = 0x10;
1333      break;
1334    case ROUTER_BUFFALO_WHRG54S:
1335    case ROUTER_BUFFALO_WLI_TX4_G54HP:
1336      diag_gpio = 0x17;
1337      bridge_gpio = 0x11;
1338      ses_gpio = 0x16;
1339      break;
1340    case ROUTER_BUFFALO_WZRRSG54:
1341      diag_gpio = 0x17;
1342      vpn_gpio = 0x11;
1343      ses_gpio = 0x16;
1344      break;
1345    case ROUTER_BUFFALO_WZRG300N:
1346      diag_gpio = 0x17;
1347      bridge_gpio = 0x11;
1348      break;
1349    case ROUTER_BUFFALO_WZRG144NH:
1350      diag_gpio = 0x13;
1351      bridge_gpio = 0x11;
1352      ses_gpio = 0x12;
1353      break;
1354#ifndef HAVE_BUFFALO
1355    case ROUTER_MOTOROLA:
1356      power_gpio = 0x01;
1357      diag_gpio = 0x11;         //power led blink / off to indicate factory defaults
1358      break;
1359    case ROUTER_RT210W:
1360      power_gpio = 0x15;
1361      diag_gpio = 0x05;         //power led blink / off to indicate factory defaults
1362      connected_gpio = 0x10;
1363      wlan_gpio = 0x13;
1364      break;
1365    case ROUTER_RT480W:
1366    case ROUTER_BELKIN_F5D7230_V2000:
1367    case ROUTER_BELKIN_F5D7231:
1368      power_gpio = 0x15;
1369      diag_gpio = 0x05;         //power led blink / off to indicate factory defaults
1370      connected_gpio = 0x10;
1371      break;
1372    case ROUTER_MICROSOFT_MN700:
1373      power_gpio = 0x06;
1374      diag_gpio = 0x16;         //power led blink / off to indicate factory defaults
1375      break;
1376    case ROUTER_ASUS_WL500GD:
1377    case ROUTER_ASUS_WL520GUGC:
1378      diag_gpio = 0x00;         //power led blink / off to indicate factory defaults
1379      break;
1380    case ROUTER_ASUS_WL500G_PRE:
1381      power_gpio = 0x11;
1382      diag_gpio = 0x01;         //power led blink / off to indicate factory defaults
1383      break;
1384    case ROUTER_WRT54G3G:
1385    case ROUTER_WRTSL54GS:
1386      power_gpio = 0x01;
1387      dmz_gpio = 0x10;
1388      connected_gpio = 0x17;    //ses orange
1389      ses_gpio = 0x15;                  //ses white
1390      ses2_gpio = 0x17;                 //ses orange   
1391      break;
1392    case ROUTER_MOTOROLA_WE800G:
1393    case ROUTER_MOTOROLA_V1:
1394      diag_gpio = 0x13;
1395      wlan_gpio = 0x11;
1396      bridge_gpio = 0x15;
1397      break;
1398    case ROUTER_DELL_TRUEMOBILE_2300:
1399    case ROUTER_DELL_TRUEMOBILE_2300_V2:
1400      power_gpio = 0x17;
1401      diag_gpio = 0x07;         //power led blink / off to indicate factory defaults
1402      wlan_gpio = 0x16;
1403      break;
1404    case ROUTER_NETGEAR_WNR834B:
1405      power_gpio = 0x14;
1406      diag_gpio = 0x15;
1407      wlan_gpio = 0x16;
1408      break;
1409    case ROUTER_SITECOM_WL105B:
1410      power_gpio = 0x03;
1411      diag_gpio = 0x13;         //power led blink / off to indicate factory defaults
1412      wlan_gpio = 0x14;
1413      break;
1414    case ROUTER_WRT150N:
1415    case ROUTER_WRT300N:
1416      power_gpio = 0x01;
1417      diag_gpio = 0x11;         //power led blink / off to indicate fac.def.
1418      break;
1419    case ROUTER_ASUS_WL500G:
1420      power_gpio = 0x10;
1421      diag_gpio = 0x00;         //power led blink /off to indicate factory defaults
1422      break;
1423    case ROUTER_ASUS_WL500W:
1424      power_gpio = 0x15;
1425      diag_gpio = 0x05;         //power led blink /off to indicate factory defaults
1426      break;
1427    case ROUTER_LINKSYS_WTR54GS:
1428      diag_gpio = 0x01;
1429      break;
1430    case ROUTER_WAP54G_V1:
1431      diag_gpio = 0x13;
1432      wlan_gpio = 0x14;         // LINK led
1433      break;
1434    case ROUTER_WAP54G_V3:
1435      ses_gpio = 0x1c;
1436      connected_gpio = 0x06;
1437      break;
1438#endif
1439    }
1440  if (type == LED_DIAG && v1func == 1)
1441    {
1442      if (act == LED_ON)
1443        C_led (1);
1444      else
1445        C_led (0);
1446    }
1447
1448  switch (type)
1449    {
1450    case LED_POWER:
1451      use_gpio = power_gpio;
1452      break;
1453    case LED_DIAG:
1454      use_gpio = diag_gpio;
1455      break;
1456    case LED_DMZ:
1457      use_gpio = dmz_gpio;
1458      break;
1459    case LED_CONNECTED:
1460      use_gpio = connected_gpio;
1461      break;
1462    case LED_BRIDGE:
1463      use_gpio = bridge_gpio;
1464      break;
1465    case LED_VPN:
1466      use_gpio = vpn_gpio;
1467      break;
1468    case LED_SES:
1469      use_gpio = ses_gpio;
1470      break;
1471    case LED_SES2:
1472      use_gpio = ses2_gpio;
1473      break;
1474    case LED_WLAN:
1475      use_gpio = wlan_gpio;
1476      break;
1477    }
1478#ifndef HAVE_XSCALE
1479  if ((use_gpio & 0x0f) != 0x0f)
1480    {
1481      gpio_value = use_gpio & 0x0f;
1482      sprintf (val, "%d", gpio_value);
1483      sprintf (enable, "%s", (use_gpio & 0x10) == 0 ? "enable" : "disable");
1484      sprintf (disable, "%s", (use_gpio & 0x10) == 0 ? "disable" : "enable");
1485#endif
1486      switch (act)
1487        {
1488        case LED_ON:
1489#ifdef HAVE_XSCALE
1490          if (type == LED_CONNECTED)
1491            eval ("gpio", "-w", gpio, "0");
1492#else
1493          eval ("gpio", enable, val);
1494#endif
1495          break;
1496        case LED_OFF:
1497#ifdef HAVE_XSCALE
1498          if (type == LED_CONNECTED)
1499            eval ("gpio", "-w", gpio, "1");
1500#else
1501          eval ("gpio", disable, val);
1502#endif
1503          break;
1504        case LED_FLASH: //will lit the led for 1 sec.
1505#ifdef HAVE_XSCALE
1506          if (type == LED_CONNECTED)
1507            {
1508              eval ("gpio", "-w", gpio, "0");
1509              sleep (1);
1510              eval ("gpio", "-w", gpio, "1");
1511            }
1512#else
1513          eval ("gpio", enable, val);
1514          sleep (1);
1515          eval ("gpio", disable, val);
1516#endif
1517          break;
1518        }
1519#ifndef HAVE_XSCALE
1520    }
1521#endif
1522  return 1;
1523
1524#endif
1525}
1526
1527
1528char *
1529get_mac_from_ip (char *ip)
1530{
1531  FILE *fp;
1532  char line[100];
1533  char ipa[50];                 // ip address
1534  char hwa[50];                 // HW address / MAC
1535  char mask[50];                // ntemask   
1536  char dev[50];                 // interface
1537  int type;                     // HW type
1538  int flags;                    // flags
1539  static char mac[20];
1540
1541
1542  if ((fp = fopen ("/proc/net/arp", "r")) == NULL)
1543    return NULL;
1544
1545  // Bypass header -- read until newline
1546  if (fgets (line, sizeof (line), fp) != (char *) NULL)
1547    {
1548      // Read the ARP cache entries.
1549      // IP address       HW type     Flags       HW address            Mask     Device
1550      // 192.168.1.1      0x1         0x2         00:90:4C:21:00:2A     *        eth0
1551      for (; fgets (line, sizeof (line), fp);)
1552        {
1553          if (sscanf
1554              (line, "%s 0x%x 0x%x %100s %100s %100s\n", ipa, &type, &flags,
1555               hwa, mask, dev) != 6)
1556            continue;
1557          //cprintf("ip1=[%s] ip2=[%s] mac=[%s] (flags & ATF_COM)=%d\n", ip, ipa, hwa, (flags & ATF_COM));
1558          if (strcmp (ip, ipa))
1559            continue;
1560          //if (!(flags & ATF_COM)) {       //ATF_COM = 0x02   completed entry (ha valid)
1561          strcpy (mac, hwa);
1562          fclose (fp);
1563          return mac;
1564          //}
1565        }
1566    }
1567
1568  fclose (fp);
1569  return "";
1570}
1571
1572struct dns_lists *
1573get_dns_list (void)
1574{
1575  char list[254];
1576  char *next, word[254];
1577  struct dns_lists *dns_list = NULL;
1578  int i, match = 0, altdns_index = 1;
1579
1580  dns_list = (struct dns_lists *) malloc (sizeof (struct dns_lists));
1581  memset (dns_list, 0, sizeof (struct dns_lists));
1582
1583  dns_list->num_servers = 0;
1584
1585  // nvram_safe_get("wan_dns") ==> Set by user
1586  // nvram_safe_get("wan_get_dns") ==> Get from DHCP, PPPoE or PPTP
1587  // The nvram_safe_get("wan_dns") priority is higher than nvram_safe_get("wan_get_dns")
1588  snprintf (list, sizeof (list), "%s %s %s", nvram_safe_get ("sv_localdns"),
1589            nvram_safe_get ("wan_dns"), nvram_safe_get ("wan_get_dns"));
1590  foreach (word, list, next)
1591  {
1592    if (strcmp (word, "0.0.0.0") && strcmp (word, ""))
1593      {
1594        match = 0;
1595        for (i = 0; i < dns_list->num_servers; i++)
1596          {                     // Skip same DNS
1597            if (!strcmp (dns_list->dns_server[i], word))
1598              match = 1;
1599          }
1600        if (!match)
1601          {
1602            snprintf (dns_list->dns_server[dns_list->num_servers],
1603                      sizeof (dns_list->dns_server[dns_list->num_servers]),
1604                      "%s", word);
1605            dns_list->num_servers++;
1606          }
1607      }
1608    if (dns_list->num_servers == 3)
1609      break;                    // We only need 3 DNS entries
1610  }
1611
1612  /* if < 3 DNS servers found, try to insert alternates */
1613  while (dns_list->num_servers < 3 && altdns_index <= 3)
1614    {
1615      char altdnsvar[32] = { 0 };
1616
1617      snprintf (altdnsvar, 31, "altdns%d", altdns_index);
1618
1619      if (strlen (nvram_safe_get (altdnsvar)) > 0)
1620        {
1621          snprintf (dns_list->dns_server[dns_list->num_servers],
1622                    sizeof (dns_list->dns_server[dns_list->num_servers]),
1623                    "%s", nvram_safe_get (altdnsvar));
1624          dns_list->num_servers++;
1625        }
1626      altdns_index++;
1627    }
1628  return dns_list;
1629}
1630
1631int
1632dns_to_resolv (void)
1633{
1634  FILE *fp_w;
1635  struct dns_lists *dns_list = NULL;
1636  int i = 0;
1637
1638  /* Save DNS to resolv.conf */
1639  if (!(fp_w = fopen (RESOLV_FILE, "w")))
1640    {
1641      perror (RESOLV_FILE);
1642      return errno;
1643    }
1644  if (nvram_invmatch ("wan_get_domain", ""))
1645    {
1646      fprintf (fp_w, "search %s\n", nvram_safe_get ("wan_get_domain"));
1647    }
1648  else if (nvram_invmatch ("wan_domain", ""))
1649    {
1650      fprintf (fp_w, "search %s\n", nvram_safe_get ("wan_domain"));
1651    }
1652  if (nvram_invmatch ("lan_domain", ""))
1653    {
1654      fprintf (fp_w, "search %s\n", nvram_safe_get ("lan_domain"));
1655    }
1656  if (nvram_match ("dnsmasq_enable", "1"))
1657    {
1658      fprintf (fp_w, "nameserver %s\n", nvram_get ("lan_ipaddr"));
1659      fclose (fp_w);
1660      if (!(fp_w = fopen (RESOLV_FORW, "w")))
1661        {
1662          perror (RESOLV_FORW);
1663          return errno;
1664        }
1665    }
1666
1667  dns_list = get_dns_list ();
1668
1669  for (i = 0; i < dns_list->num_servers; i++)
1670    fprintf (fp_w, "nameserver %s\n", dns_list->dns_server[i]);
1671
1672  /* Put a pseudo DNS IP to trigger Connect On Demand */
1673  if (dns_list->num_servers == 0 &&
1674      (nvram_match ("wan_proto", "pppoe") || nvram_match ("wan_proto", "pptp")
1675       || nvram_match ("wan_proto", "l2tp"))
1676      && nvram_match ("ppp_demand", "1"))
1677    fprintf (fp_w, "nameserver 1.1.1.1\n");
1678
1679  fclose (fp_w);
1680  if (dns_list)
1681    free (dns_list);
1682
1683  eval ("touch", "/tmp/hosts");
1684
1685  return 1;
1686}
1687
1688/* Example:
1689 * lan_ipaddr = 192.168.1.1
1690 * get_dns_ip("lan_ipaddr", 1); produces "168"
1691 */
1692int
1693get_single_ip (char *ipaddr, int which)
1694{
1695  int ip[4] = { 0, 0, 0, 0 };
1696  int ret;
1697
1698  ret = sscanf (ipaddr, "%d.%d.%d.%d", &ip[0], &ip[1], &ip[2], &ip[3]);
1699
1700  return ip[which];
1701}
1702
1703char *
1704get_complete_lan_ip (char *ip)
1705{
1706  static char ipaddr[20];
1707
1708  int i[4];
1709
1710  if (sscanf
1711      (nvram_safe_get ("lan_ipaddr"), "%d.%d.%d.%d", &i[0], &i[1], &i[2],
1712       &i[3]) != 4)
1713    return "0.0.0.0";
1714
1715  snprintf (ipaddr, sizeof (ipaddr), "%d.%d.%d.%s", i[0], i[1], i[2], ip);
1716
1717  return ipaddr;
1718}
1719
1720char *
1721get_wan_face (void)
1722{
1723  static char localwanface[IFNAMSIZ];
1724/*  if (nvram_match ("pptpd_client_enable", "1"))
1725    {
1726        strncpy (localwanface, "ppp0", IFNAMSIZ);
1727        return localwanface;
1728    }*/
1729  if (nvram_match ("wan_proto", "pptp") || nvram_match ("wan_proto", "l2tp")
1730      || nvram_match ("wan_proto", "pppoe"))
1731    {
1732      if (nvram_match ("pppd_pppifname", ""))
1733        strncpy (localwanface, "ppp0", IFNAMSIZ);
1734      else
1735        strncpy (localwanface, nvram_safe_get ("pppd_pppifname"), IFNAMSIZ);
1736    }
1737#ifndef HAVE_MADWIFI
1738  else if (getSTA ())
1739    {
1740        strcpy (localwanface, getSTA ());
1741    }
1742#else
1743  else if (getSTA ())
1744    {
1745      if (nvram_match ("wifi_bonding", "1"))
1746        strcpy (localwanface, "bond0");
1747      else
1748        strcpy (localwanface, getSTA ());
1749    }
1750#endif
1751  else
1752    strncpy (localwanface, nvram_safe_get ("wan_ifname"), IFNAMSIZ);
1753
1754  return localwanface;
1755}
1756
1757int
1758get_ppp_pid (char *file)
1759{
1760  char buf[80];
1761  int pid = -1;
1762  if (file_to_buf (file, buf, sizeof (buf)))
1763    {
1764      char tmp[80], tmp1[80];
1765      snprintf (tmp, sizeof (tmp), "/var/run/%s.pid", buf);
1766      file_to_buf (tmp, tmp1, sizeof (tmp1));
1767      pid = atoi (tmp1);
1768    }
1769  return pid;
1770}
1771
1772/*
1773 =====================================================================================
1774                                by tallest
1775 =====================================================================================
1776 */
1777
1778
1779int
1780check_wan_link (int num)
1781{
1782  int wan_link = 0;
1783
1784  if (nvram_match ("wan_proto", "pptp")
1785      || nvram_match ("wan_proto", "l2tp")
1786      || nvram_match ("wan_proto", "pppoe")
1787      || nvram_match ("wan_proto", "heartbeat"))
1788    {
1789      FILE *fp;
1790      char filename[80];
1791      char *name;
1792
1793      if (num == 0)
1794        strcpy (filename, "/tmp/ppp/link");
1795      if ((fp = fopen (filename, "r")))
1796        {
1797          int pid = -1;
1798          fclose (fp);
1799          if (nvram_match ("wan_proto", "heartbeat"))
1800            {
1801              char buf[20];
1802              file_to_buf ("/tmp/ppp/link", buf, sizeof (buf));
1803              pid = atoi (buf);
1804            }
1805          else
1806            pid = get_ppp_pid (filename);
1807
1808          name = find_name_by_proc (pid);
1809          if (!strncmp (name, "pppoecd", 7) ||  // for PPPoE
1810              !strncmp (name, "pppd", 4) ||     // for PPTP
1811              !strncmp (name, "bpalogin", 8))   // for HeartBeat
1812            wan_link = 1;       //connect
1813          else
1814            {
1815              printf ("The %s had been died, remove %s\n",
1816                      nvram_safe_get ("wan_proto"), filename);
1817              wan_link = 0;     // For some reason, the pppoed had been died, by link file still exist.
1818              unlink (filename);
1819            }
1820        }
1821    }
1822  else
1823    {
1824      if (nvram_invmatch ("wan_ipaddr", "0.0.0.0"))
1825        wan_link = 1;
1826    }
1827
1828  return wan_link;
1829}
1830
1831int
1832get_int_len (int num)
1833{
1834  char buf[80];
1835
1836  snprintf (buf, sizeof (buf), "%d", num);
1837
1838  return strlen (buf);
1839}
1840
1841int
1842file_to_buf (char *path, char *buf, int len)
1843{
1844  FILE *fp;
1845
1846  memset (buf, 0, len);
1847
1848  if ((fp = fopen (path, "r")))
1849    {
1850      fgets (buf, len, fp);
1851      fclose (fp);
1852      return 1;
1853    }
1854
1855  return 0;
1856}
1857
1858int
1859buf_to_file (char *path, char *buf)
1860{
1861  FILE *fp;
1862
1863  if ((fp = fopen (path, "w")))
1864    {
1865      fprintf (fp, "%s", buf);
1866      fclose (fp);
1867      return 1;
1868    }
1869
1870  return 0;
1871}
1872
1873
1874#define READ_BUF_SIZE 254
1875/* from busybox find_pid_by_name.c */
1876pid_t *
1877find_pid_by_name (char *pidName)
1878{
1879  DIR *dir;
1880  struct dirent *next;
1881  pid_t *pidList = NULL;
1882  int i = 0;
1883
1884  dir = opendir ("/proc");
1885
1886  while ((next = readdir (dir)) != NULL)
1887    {
1888      FILE *status;
1889      char filename[READ_BUF_SIZE];
1890      char buffer[READ_BUF_SIZE];
1891      char name[READ_BUF_SIZE];
1892
1893      /* Must skip ".." since that is outside /proc */
1894      if (strcmp (next->d_name, "..") == 0)
1895        continue;
1896
1897      /* If it isn't a number, we don't want it */
1898      if (!isdigit (*next->d_name))
1899        continue;
1900
1901      sprintf (filename, "/proc/%s/status", next->d_name);
1902      if (!(status = fopen (filename, "r")))
1903        {
1904          continue;
1905        }
1906      if (fgets (buffer, READ_BUF_SIZE - 1, status) == NULL)
1907        {
1908          fclose (status);
1909          continue;
1910        }
1911      fclose (status);
1912
1913      /* Buffer should contain a string like "Name:   binary_name" */
1914      sscanf (buffer, "%*s %s", name);
1915      //printf("buffer=[%s] name=[%s]\n",buffer,name);
1916      if (strcmp (name, pidName) == 0)
1917        {
1918          pidList = realloc (pidList, sizeof (pid_t) * (i + 2));
1919          pidList[i++] = strtol (next->d_name, NULL, 0);
1920        }
1921    }
1922
1923  if (pidList)
1924    pidList[i] = 0;
1925  else
1926    {
1927      pidList = realloc (pidList, sizeof (pid_t));
1928      pidList[0] = -1;
1929    }
1930  return pidList;
1931
1932}
1933
1934/* Find first process pid with same name from ps command */
1935int
1936find_pid_by_ps (char *pidName)
1937{
1938  FILE *fp;
1939  int pid = -1;
1940  char line[254];
1941
1942  if ((fp = popen ("ps", "r")))
1943    {
1944      while (fgets (line, sizeof (line), fp) != NULL)
1945        {
1946          if (strstr (line, pidName))
1947            {
1948              sscanf (line, "%d", &pid);
1949              printf ("%s pid is %d\n", pidName, pid);
1950              break;
1951            }
1952        }
1953      pclose (fp);
1954    }
1955
1956  return pid;
1957}
1958
1959/* Find process name by pid from /proc directory */
1960char *
1961find_name_by_proc (int pid)
1962{
1963  FILE *fp;
1964  char line[254];
1965  char filename[80];
1966  static char name[80];
1967
1968  snprintf (filename, sizeof (filename), "/proc/%d/status", pid);
1969
1970  if ((fp = fopen (filename, "r")))
1971    {
1972      fgets (line, sizeof (line), fp);
1973      /* Buffer should contain a string like "Name:   binary_name" */
1974      sscanf (line, "%*s %s", name);
1975      fclose (fp);
1976      return name;
1977    }
1978
1979  return "";
1980}
1981
1982/* Find all process pid with same name from ps command */
1983int *
1984find_all_pid_by_ps (char *pidName)
1985{
1986  FILE *fp;
1987  int pid = -1;
1988  char line[254];
1989  int *pidList = NULL;
1990  int i = 0;
1991  printf ("Search for %s\n", pidName);
1992  if ((fp = popen ("ps", "r")))
1993    {
1994      while (fgets (line, sizeof (line), fp) != NULL)
1995        {
1996          if (strstr (line, pidName))
1997            {
1998              sscanf (line, "%d", &pid);
1999              printf ("%s pid is %d\n", pidName, pid);
2000              pidList = realloc (pidList, sizeof (int) * (i + 2));
2001              pidList[i++] = pid;
2002            }
2003        }
2004      pclose (fp);
2005    }
2006  if (pidList)
2007    pidList[i] = 0;
2008  else
2009    {
2010      pidList = realloc (pidList, sizeof (int));
2011      pidList[0] = -1;
2012    }
2013  printf ("Search done...\n");
2014
2015  return pidList;
2016}
2017
2018
2019int
2020count_processes (char *pidName)
2021{
2022  FILE *fp;
2023  char line[254];
2024  int i = 0;
2025  printf ("Search for %s\n", pidName);
2026  if ((fp = popen ("ps", "r")))
2027    {
2028      while (fgets (line, sizeof (line), fp) != NULL)
2029        {
2030          if (strstr (line, pidName))
2031            {
2032              i++;
2033            }
2034        }
2035      pclose (fp);
2036    }
2037  printf ("Search done... %d\n", i);
2038
2039  return i;
2040}
2041
2042void
2043encode (char *buf, int len)
2044{
2045  int i;
2046  char ch;
2047
2048  for (i = 0; i < len; i++)
2049    {
2050      ch = (buf[i] & 0x03) << 6;
2051      buf[i] = (buf[i] >> 2);
2052      buf[i] &= 0x3f;
2053      buf[i] |= ch;
2054      buf[i] = ~buf[i];
2055    }
2056}
2057
2058void
2059decode (char *buf, int len)
2060{
2061  int i;
2062  char ch;
2063
2064  for (i = 0; i < len; i++)
2065    {
2066      ch = (buf[i] & 0xC0) >> 6;
2067      buf[i] = (buf[i] << 2) | ch;
2068      buf[i] = ~buf[i];
2069    }
2070}
2071
2072/*      v1.41.7 => 014107
2073 *      v1.2    => 0102
2074 */
2075long
2076convert_ver (char *ver)
2077{
2078  char buf[10];
2079  int v[3];
2080  int ret;
2081
2082  ret = sscanf (ver, "v%d.%d.%d", &v[0], &v[1], &v[2]);
2083
2084  if (ret == 2)
2085    {
2086      snprintf (buf, sizeof (buf), "%02d%02d", v[0], v[1]);
2087      return atol (buf);
2088    }
2089  else if (ret == 3)
2090    {
2091      snprintf (buf, sizeof (buf), "%02d%02d%02d", v[0], v[1], v[2]);
2092      return atol (buf);
2093    }
2094  else
2095    return -1;
2096}
2097
2098/* To avoid user to download old image that is not support intel flash to new hardware with intel flash.
2099 */
2100int
2101check_flash (void)
2102{
2103  // The V2 image can support intel flash completely, so we don't want to check.
2104  if (check_hw_type () == BCM4712_CHIP)
2105    return FALSE;
2106
2107  // The V1.X some images cann't support intel flash, so we want to avoid user to downgrade.
2108  if (nvram_match ("skip_amd_check", "1"))
2109    {
2110      if (strstr (nvram_safe_get ("flash_type"), "Intel")
2111          && nvram_invmatch ("skip_intel_check", "1"))
2112        return TRUE;
2113      else
2114        return FALSE;
2115    }
2116  else                          // Cann't downgrade to old firmware version, no matter AMD or Intel flash
2117    return TRUE;
2118}
2119
2120int
2121check_action (void)
2122{
2123  char buf[80] = "";
2124
2125  if (file_to_buf (ACTION_FILE, buf, sizeof (buf)))
2126    {
2127      if (!strcmp (buf, "ACT_TFTP_UPGRADE"))
2128        {
2129          fprintf (stderr, "Upgrading from tftp now ...\n");
2130          return ACT_TFTP_UPGRADE;
2131        }
2132#ifdef HAVE_HTTPS
2133      else if (!strcmp (buf, "ACT_WEBS_UPGRADE"))
2134        {
2135          fprintf (stderr, "Upgrading from web (https) now ...\n");
2136          return ACT_WEBS_UPGRADE;
2137        }
2138#endif
2139      else if (!strcmp (buf, "ACT_WEB_UPGRADE"))
2140        {
2141          fprintf (stderr, "Upgrading from web (http) now ...\n");
2142          return ACT_WEB_UPGRADE;
2143        }
2144      else if (!strcmp (buf, "ACT_SW_RESTORE"))
2145        {
2146          fprintf (stderr, "Receiving restore command from web ...\n");
2147          return ACT_SW_RESTORE;
2148        }
2149      else if (!strcmp (buf, "ACT_HW_RESTORE"))
2150        {
2151          fprintf (stderr,
2152                   "Receiving restore command from resetbutton ...\n");
2153          return ACT_HW_RESTORE;
2154        }
2155      else if (!strcmp (buf, "ACT_NVRAM_COMMIT"))
2156        {
2157          fprintf (stderr, "Committing nvram now ...\n");
2158          return ACT_NVRAM_COMMIT;
2159        }
2160      else if (!strcmp (buf, "ACT_ERASE_NVRAM"))
2161        {
2162          fprintf (stderr, "Erasing nvram now ...\n");
2163          return ACT_ERASE_NVRAM;
2164        }
2165    }
2166  //fprintf(stderr, "Waiting for upgrading....\n");
2167  return ACT_IDLE;
2168}
2169
2170int
2171check_now_boot (void)
2172{
2173  char *ver = nvram_safe_get ("pmon_ver");
2174  char *cfe = nvram_safe_get ("CFEver");
2175  // for 4712
2176  // The boot_ver value is lower v2.0 (no included)
2177  if (!strncmp (ver, "PMON", 4))
2178    {
2179      cprintf ("The boot is PMON\n");
2180      return PMON_BOOT;
2181    }
2182  // for 4712
2183  // The boot_ver value is higher v2.0 (included)
2184  else if (!strncmp (ver, "CFE", 3))
2185    {
2186      cprintf ("The boot is CFE\n");
2187      return CFE_BOOT;
2188    }
2189  else if (!strncmp (ver, "2", 1))
2190    {
2191      cprintf ("The boot is CFE %s\n", ver);
2192      return CFE_BOOT;
2193    }
2194  else if (!strncmp (cfe, "MotoWR", 6))
2195    {
2196      cprintf ("The boot is Motorola CFE\n");
2197      return CFE_BOOT;
2198    }
2199  else
2200    {
2201      cprintf ("The boot is UNKNOWN\n");
2202      return UNKNOWN_BOOT;
2203    }
2204}
2205
2206void
2207show_hw_type (int type)
2208{
2209  cprintf ("The chipset is ");
2210  if (type == BCM4702_CHIP)
2211    cprintf ("BCM4702\n");
2212  else if (type == BCM5325E_CHIP)
2213    cprintf ("BCM4712L + BCM5325E\n");
2214  else if (type == BCM5365_CHIP)
2215    cprintf ("BCM5365\n");
2216  else if (type == BCM5350_CHIP)
2217    cprintf ("BCM5350\n");
2218  else if (type == BCM4704_BCM5325F_CHIP)
2219    cprintf ("BCM4704 + BCM5325F\n");
2220  else if (type == BCM5352E_CHIP)
2221    cprintf ("BCM5352E\n");
2222  else if (type == BCM5354G_CHIP)
2223    cprintf ("BCM5354G\n");
2224  else if (type == BCM4712_CHIP)
2225    cprintf ("BCM4712 + ADMtek\n");
2226  else if (type == BCM4704_BCM5325F_EWC_CHIP)
2227    cprintf ("BCM4704 + BCM5325F for EWC\n");
2228  else
2229    cprintf ("not defined\n");
2230
2231}
2232
2233int
2234check_hw_type (void)
2235{
2236
2237  char *boardtype = nvram_safe_get ("boardtype");
2238  uint boardflags = strtoul (nvram_safe_get ("boardflags"), NULL, 0);
2239  uint btype = strtoul (boardtype, NULL, 0);
2240
2241  if (!strncmp (boardtype, "bcm94710", 8))
2242    return BCM4702_CHIP;
2243  else if (btype == 0x0708 && !(boardflags & BFL_ENETADM))
2244    return BCM5325E_CHIP;
2245  else if (btype == 0x456 && getRouterBrand () == ROUTER_BELKIN_F5D7231)  //stupid Belkin!
2246    return BCM5352E_CHIP;   
2247  else if (btype == 0x456)
2248    return BCM5350_CHIP;
2249  else if (!strncmp (boardtype, "bcm95365", 8))
2250    return BCM5365_CHIP;   
2251  else if (btype == 0x048e)
2252    return BCM5354G_CHIP;
2253  else if (btype == 0x042f && !(boardflags & BFL_ENETADM))
2254    return BCM4704_BCM5325F_CHIP;
2255  else if (btype == 0x478)
2256    return BCM4705_BCM5397_EWC_CHIP;
2257  else if (btype == 0x0467)
2258    return BCM5352E_CHIP;
2259  else if (btype == 0x0101 || btype == 0x0446)  //0x446 is wap54g v2
2260    return BCM4712_CHIP;
2261  else if (btype == 0x0472 && !(boardflags & BFL_ENETADM))
2262    return BCM4704_BCM5325F_EWC_CHIP;
2263  else
2264    return NO_DEFINE_CHIP;
2265}
2266
2267int
2268is_exist (char *filename)
2269{
2270  FILE *fp;
2271
2272  if ((fp = fopen (filename, "r")))
2273    {
2274      fclose (fp);
2275      return 1;
2276    }
2277  return 0;
2278}
2279
2280int
2281ct_openlog (const char *ident, int option, int facility, char *log_name)
2282{
2283  int level = atoi (nvram_safe_get (log_name));
2284
2285  switch (level)
2286    {
2287    case CONSOLE_ONLY:
2288      break;
2289    }
2290  return level;
2291}
2292
2293
2294void
2295ct_syslog (int level, int enable, const char *fmt, ...)
2296{
2297  char buf[1000];
2298  va_list args;
2299
2300  va_start (args, fmt);
2301  vsnprintf (buf, sizeof (buf), fmt, args);
2302  va_end (args);
2303
2304  switch (enable)
2305    {
2306    case CONSOLE_ONLY:
2307      cprintf ("[%d] %s\n", getpid (), buf);    // print to console
2308      break;
2309    }
2310}
2311
2312void
2313ct_logger (int level, const char *fmt, ...)
2314{
2315}
2316
2317void
2318set_ip_forward (char c)
2319{
2320  FILE *fp;
2321
2322  if ((fp = fopen ("/proc/sys/net/ipv4/ip_forward", "r+")))
2323    {
2324      fputc (c, fp);
2325      fclose (fp);
2326    }
2327  else
2328    {
2329      perror ("/proc/sys/net/ipv4/ip_forward");
2330    }
2331}
2332
2333
2334static char *device_name[] = {
2335  "eth0",
2336  "qos0"
2337};
2338
2339char *
2340get_device_name (void)
2341{
2342  int i;
2343
2344  switch (check_hw_type ())
2345    {
2346    case BCM5325E_CHIP:
2347    case BCM5350_CHIP:
2348    case BCM5365_CHIP:
2349    case BCM4704_BCM5325F_CHIP:
2350    case BCM5352E_CHIP:
2351    case BCM5354G_CHIP:
2352      i = 0;
2353      break;
2354    case BCM4702_CHIP:
2355    case BCM4712_CHIP:
2356    default:
2357      i = 1;
2358      break;
2359    }
2360
2361  return device_name[i];
2362}
2363
2364char *
2365strncpyz (char *dest, char const *src, size_t size)
2366{
2367  if (!size--)
2368    return dest;
2369  strncpy (dest, src, size);
2370  dest[size] = 0;               /* Make sure the string is null terminated */
2371  return dest;
2372}
2373
2374static int
2375sockets_open (int domain, int type, int protocol)
2376{
2377  int fd = socket (domain, type, protocol);
2378
2379  if (fd < 0)
2380    cprintf ("sockets_open: no usable address was found.\n");
2381  return fd;
2382}
2383
2384int
2385sys_netdev_ioctl (int family, int socket, char *if_name, int cmd,
2386                  struct ifreq *ifr)
2387{
2388  int rc, s;
2389
2390  if ((s = socket) < 0)
2391    {
2392      if ((s = sockets_open (family, family == AF_PACKET ? SOCK_PACKET :
2393                             SOCK_DGRAM,
2394                             family == AF_PACKET ? htons (ETH_P_ALL) : 0)) <
2395          0)
2396        {
2397          cprintf ("sys_netdev_ioctl: failed\n");
2398          return -1;
2399        }
2400    }
2401  strncpyz (ifr->ifr_name, if_name, IFNAMSIZ);
2402  rc = ioctl (s, cmd, ifr);
2403  if (socket < 0)
2404    close (s);
2405  return rc;
2406}
2407
2408int
2409set_register_value (unsigned short port_addr, unsigned short option_content)
2410{
2411  struct ifreq ifr;
2412  struct mii_ioctl_data stats;
2413
2414  stats.phy_id = port_addr;
2415  stats.val_in = option_content;
2416
2417  ifr.ifr_data = (void *) &stats;
2418
2419  if (sys_netdev_ioctl (AF_INET, -1, get_device_name (), SIOCSMIIREG, &ifr) <
2420      0)
2421    return -1;
2422
2423  return 0;
2424}
2425
2426unsigned long
2427get_register_value (unsigned short id, unsigned short num)
2428{
2429  struct ifreq ifr;
2430  struct mii_ioctl_data stats;
2431
2432  stats.phy_id = id;
2433  stats.reg_num = num;
2434  stats.val_in = 0;
2435  stats.val_out = 0;
2436
2437  ifr.ifr_data = (void *) &stats;
2438
2439  sys_netdev_ioctl (AF_INET, -1, get_device_name (), SIOCGMIIREG, &ifr);
2440
2441  return ((stats.val_in << 16) | stats.val_out);
2442}
2443
2444
2445struct wl_assoc_mac *
2446get_wl_assoc_mac (int *c)
2447{
2448  FILE *fp;
2449  struct wl_assoc_mac *wlmac = NULL;
2450  int count;
2451  char line[80];
2452  char list[2][20];
2453
2454  wlmac = NULL;
2455  count = *c = 0;
2456
2457#ifdef HAVE_MSSID
2458  char assoccmd[4][32] =
2459    { "wl assoclist", "wl -i wl0.1 assoclist", "wl -i wl0.2 assoclist", "wl -i wl0.3 assoclist" };
2460  int ifcnt = 4;
2461#else
2462  char assoccmd[1][16] = { "wl assoclist" };
2463  int ifcnt = 1;
2464#endif
2465  int i;
2466  int gotit = 0;
2467//  fprintf(stderr,"assoclist\n");
2468
2469  for (i = 0; i < ifcnt; i++)
2470    {
2471      if (i)
2472        {
2473        char checkif[12];
2474        sprintf(checkif,"wl0.%d",i);
2475        if (!ifexists(checkif))
2476            break;
2477        }
2478      if ((fp = popen (assoccmd[i], "r")))
2479        {
2480          gotit = 1;
2481          while (fgets (line, sizeof (line), fp) != NULL)
2482            {
2483              strcpy (list[0], "");
2484              strcpy (list[1], "");
2485
2486              if (sscanf (line, "%s %s", list[0], list[1]) != 2)        // assoclist 00:11:22:33:44:55
2487                continue;
2488              if (strcmp (list[0], "assoclist"))
2489                continue;
2490
2491              wlmac =
2492                realloc (wlmac, sizeof (struct wl_assoc_mac) * (count + 1));
2493
2494              memset (&wlmac[count], 0, sizeof (struct wl_assoc_mac));
2495              strncpy (wlmac[count].mac, list[1], sizeof (wlmac[0].mac));
2496              count++;
2497            }
2498
2499          pclose (fp);
2500        }
2501    }
2502
2503  if (gotit)
2504    {
2505      //cprintf("Count of wl assoclist mac is %d\n", count);
2506      *c = count;
2507      return wlmac;
2508    }
2509  else
2510    return NULL;
2511}
2512
2513struct mtu_lists mtu_list[] = {
2514#ifdef BUFFALO_JP
2515  {"pppoe", "576", "1454"},
2516#else
2517  {"pppoe", "576", "1492"},
2518#endif
2519
2520  {"pptp", "576", "1460"},
2521
2522  {"l2tp", "576", "1460"},
2523
2524  {"dhcp", "576", "1500"},
2525  {"static", "576", "1500"},
2526  {"heartbeat", "576", "1500"},
2527  {"default", "576", "1500"},   // The value must be at last
2528};
2529
2530struct mtu_lists *
2531get_mtu (char *proto)
2532{
2533  struct mtu_lists *v = NULL;
2534
2535  for (v = mtu_list; v < &mtu_list[STRUCT_LEN (mtu_list)]; v++)
2536    {
2537      if (!strcmp (proto, v->proto))
2538        return v;
2539    }
2540  return v;                     // Use default settings
2541}
2542
2543void
2544set_host_domain_name (void)
2545{
2546  char *wan_hostname = nvram_safe_get ("wan_hostname");
2547  char *wan_domain = nvram_safe_get ("wan_domain");
2548
2549  /* Allow you to use gethostname to get Host Name */
2550  /* If wan_hostname is blank then we do nothing, we leave to what it was set at boot */
2551  if (strlen (wan_hostname) > 0)
2552    sethostname (wan_hostname, strlen (wan_hostname));
2553
2554  /* Allow you to use getdomainname to get Domain Name */
2555  if (strlen (wan_domain) > 0 && strlen (wan_domain) <= 64)     //no more than 64
2556    setdomainname (wan_domain, strlen (wan_domain));
2557  else
2558    {
2559      char *wan_get_domain = nvram_safe_get ("wan_get_domain");
2560      setdomainname (wan_get_domain, strlen (wan_get_domain));
2561    }
2562}
2563
2564int
2565first_time (void)
2566{
2567  struct sysinfo info;
2568
2569  sysinfo (&info);
2570  if (info.uptime < 20L)
2571    return 1;
2572  return 0;
2573}
2574
2575int
2576check_vlan_support (void)
2577{
2578#if defined(HAVE_GEMTEK) || defined(HAVE_RB500) || defined(HAVE_XSCALE) || defined(HAVE_MAGICBOX) || defined(HAVE_FONERA) || defined(HAVE_MERAKI) || defined(HAVE_LS2) || defined(HAVE_WHRAG108) || defined(HAVE_X86) || defined(HAVE_CA8) || defined(HAVE_TW6600) || defined(HAVE_PB42) || defined(HAVE_LS5)
2579  return 0;
2580#else
2581
2582
2583  int brand = getRouterBrand ();
2584  switch (brand)
2585    {
2586#ifndef HAVE_BUFFALO
2587    case ROUTER_ASUS_WL500GD:
2588      return 1;
2589      break;
2590#endif
2591    case ROUTER_BUFFALO_WLAG54C:
2592    case ROUTER_BUFFALO_WLA2G54C:
2593#ifndef HAVE_BUFFALO
2594    case ROUTER_LINKSYS_WRT55AG:
2595    case ROUTER_MOTOROLA_V1:
2596    case ROUTER_MOTOROLA_WE800G:
2597    case ROUTER_WAP54G_V1:
2598    case ROUTER_SITECOM_WL105B:
2599    case ROUTER_SITECOM_WL111:
2600    case ROUTER_BUFFALO_WLI2_TX1_G54:
2601    case ROUTER_BUFFALO_WLI_TX4_G54HP:
2602    case ROUTER_BRCM4702_GENERIC:
2603    case ROUTER_ASUS_WL500G:
2604    case ROUTER_BELKIN_F5D7230_V2000:
2605#endif
2606      return 0;
2607      break;
2608    }
2609
2610  uint boardflags = strtoul (nvram_safe_get ("boardflags"), NULL, 0);
2611  if (boardflags & BFL_ENETVLAN)
2612    return 1;
2613
2614  if (nvram_match ("boardtype", "bcm94710dev")
2615      || nvram_match ("boardtype", "0x0101") || (boardflags & 0x0100))
2616    return 1;
2617  else
2618    return 0;
2619#endif
2620}
2621
2622#ifdef CDEBUG
2623int
2624coreleft (void)
2625{
2626  struct sysinfo info;
2627  sysinfo (&info);
2628  return info.freeram;
2629}
2630
2631int
2632mcoreleft (void)
2633{
2634  struct mallinfo minfo;
2635  minfo = mallinfo ();
2636  return minfo.uordblks;
2637  //int uordblks; /* total allocated space */
2638
2639}
2640#endif
2641
2642#define sin_addr(s) (((struct sockaddr_in *)(s))->sin_addr)
2643
2644//#define WDS_DEBUG 1
2645#undef WDS_DEBUG
2646#ifdef WDS_DEBUG
2647FILE *fp;
2648#endif
2649
2650
2651int
2652wds_dev_config (int dev, int up)
2653{
2654  char wds_var[32] = "";
2655  char wds_enable_var[32] = "";
2656  char wds_dev[32] = "";
2657  char *wds = (void *) 0;
2658  char wds_gw_var[32] = "";
2659  char cmd[100] = "";
2660  char *gw = (void *) 0;
2661  int s = -1;
2662  struct ifreq ifr;
2663
2664#ifdef WDS_DEBUG
2665  fp = fopen ("/tmp/.wds_debug.log", "a");
2666#endif
2667
2668  memset (&ifr, 0, sizeof (struct ifreq));
2669
2670  snprintf (wds_var, 31, "wl_wds%d", dev);
2671  snprintf (wds_enable_var, 31, "%s_enable", wds_var);
2672
2673  if ((wds = nvram_safe_get (wds_enable_var)) == NULL ||
2674      strcmp (wds, "0") == 0)
2675    return -1;
2676#ifdef HAVE_MSSID
2677  snprintf (wds_dev, 31, "wds0.%d", dev + 1);
2678#else
2679  snprintf (wds_dev, 31, "wds0.491%d", 50 + dev + 1);
2680#endif
2681  snprintf (ifr.ifr_name, IFNAMSIZ, wds_dev);
2682#ifdef WDS_DEBUG
2683  fprintf (fp, "opening kernelsocket\n");
2684#endif
2685  if ((s = socket (AF_INET, SOCK_RAW, IPPROTO_RAW)) < 0)
2686    return -1;
2687
2688  if (up)
2689    {
2690      char wds_hwaddr_var[32] = "";
2691      char wds_ip_var[32] = "";
2692      char wds_netmask_var[32] = "";
2693      char *wds_list = (void *) 0;
2694      char *hwaddr = (void *) 0;
2695      char *ip = (void *) 0;
2696      char *netmask = (void *) 0;
2697
2698#ifdef WDS_DEBUG
2699      fprintf (fp, "running up\n");
2700#endif
2701
2702      wds_list = nvram_safe_get ("wl0_wds");
2703      if (wds_list == (void *) 0 || strlen (wds_list) <= 0)
2704        return 0;
2705
2706      snprintf (wds_hwaddr_var, 31, "%s_hwaddr", wds_var);
2707      snprintf (wds_ip_var, 31, "%s_ipaddr", wds_var);
2708      snprintf (wds_netmask_var, 31, "%s_netmask", wds_var);
2709
2710      hwaddr = nvram_safe_get (wds_hwaddr_var);
2711      ip = nvram_safe_get (wds_ip_var);
2712      netmask = nvram_safe_get (wds_netmask_var);
2713
2714      if (!strstr (wds_list, hwaddr))
2715      {
2716        close (s);
2717        return -1;
2718      }
2719
2720#ifdef WDS_DEBUG
2721      fprintf (fp, "checking validity\n");
2722#endif
2723
2724      if (!sv_valid_hwaddr (hwaddr) || !sv_valid_ipaddr (ip)
2725          || !sv_valid_ipaddr (netmask))
2726      {
2727        close (s);
2728        return -1;
2729      }
2730
2731#ifdef WDS_DEBUG
2732      fprintf (fp, "valid mac %s ip %s nm %s\n", hwaddr, ip, netmask);
2733#endif
2734
2735      snprintf (cmd, 99, "ifconfig %s down", wds_dev);
2736      system2 (cmd);
2737
2738      snprintf (cmd, 99, "ifconfig %s %s netmask %s up", wds_dev, ip,
2739                netmask);
2740      system2 (cmd);
2741
2742      snprintf (wds_gw_var, 31, "%s_gw", wds_var);
2743      gw = nvram_safe_get (wds_gw_var);
2744      if (strcmp (gw, "0.0.0.0") != 0)
2745        {
2746          get_network (ip, netmask);
2747          route_del (wds_dev, 0, ip, gw, netmask);
2748          route_add (wds_dev, 0, ip, gw, netmask);
2749        }
2750
2751    }
2752  else
2753    {
2754#ifdef WDS_DEBUG
2755      fprintf (fp, "running down\n");
2756#endif
2757      snprintf (cmd, 99, "ifconfig %s down", wds_dev);
2758      system2 (cmd);
2759
2760    }
2761
2762#ifdef WDS_DEBUG
2763  fprintf (fp, "running ioctl\n");
2764  fclose (fp);
2765#endif
2766
2767  close (s);
2768
2769  return 0;
2770}
2771
2772
2773int
2774ishexit (char c)
2775{
2776
2777  if (strchr ("01234567890abcdefABCDEF", c) != (char *) 0)
2778    return 1;
2779
2780  return 0;
2781}
2782
2783
2784/* Example:
2785 * legal_hwaddr("00:11:22:33:44:aB"); return true;
2786 * legal_hwaddr("00:11:22:33:44:5"); return false;
2787 * legal_hwaddr("00:11:22:33:44:HH"); return false;
2788 */
2789int
2790sv_valid_hwaddr (char *value)
2791{
2792  unsigned int hwaddr[6];
2793  int tag = TRUE;
2794  int i, count;
2795
2796  /* Check for bad, multicast, broadcast, or null address */
2797  for (i = 0, count = 0; *(value + i); i++)
2798    {
2799      if (*(value + i) == ':')
2800        {
2801          if ((i + 1) % 3 != 0)
2802            {
2803              tag = FALSE;
2804              break;
2805            }
2806          count++;
2807        }
2808      else if (ishexit (*(value + i)))  /* one of 0 1 2 3 4 5 6 7 8 9 a b c d e f A B C D E F */
2809        continue;
2810      else
2811        {
2812          tag = FALSE;
2813          break;
2814        }
2815    }
2816
2817  if (!tag || i != 17 || count != 5)    /* must have 17's characters and 5's ':' */
2818    tag = FALSE;
2819  else if (sscanf (value, "%x:%x:%x:%x:%x:%x",
2820                   &hwaddr[0], &hwaddr[1], &hwaddr[2],
2821                   &hwaddr[3], &hwaddr[4], &hwaddr[5]) != 6)
2822    {
2823      tag = FALSE;
2824    }
2825  else
2826    tag = TRUE;
2827#ifdef WDS_DEBUG
2828  if (tag == FALSE)
2829    fprintf (fp, "failed valid_hwaddr\n");
2830#endif
2831
2832  return tag;
2833}
2834
2835
2836int
2837sv_valid_range (char *value, int low, int high)
2838{
2839  if (!isdigit (value[0]) || atoi (value) < low || atoi (value) > high)
2840    return FALSE;
2841  else
2842    return TRUE;
2843
2844}
2845
2846int
2847sv_valid_statics (char *value)
2848{
2849  char ip[16] = { 0 }, mac[18] =
2850  {
2851  0}, hostname[255] =
2852  {
2853  0}, *p = value;
2854
2855  if (NULL == value)
2856    return FALSE;
2857
2858  do
2859    {
2860      while (isspace (*p++) && p - value < strlen (value))
2861        ;
2862
2863      if (p - value >= strlen (value))
2864        return FALSE;
2865
2866      if (sscanf (p, "%15s%17s%254s", ip, mac, hostname) < 3)
2867        return FALSE;
2868
2869      if (!sv_valid_ipaddr (ip) || !sv_valid_hwaddr (mac)
2870          || strlen (hostname) <= 0)
2871        return FALSE;
2872
2873    }
2874  while ((p = strpbrk (p, "\n\r")) && p - value < strlen (value));
2875
2876  return TRUE;
2877}
2878
2879/* Example:
2880 * legal_ipaddr("192.168.1.1"); return true;
2881 * legal_ipaddr("192.168.1.1111"); return false;
2882 */
2883int
2884sv_valid_ipaddr (char *value)
2885{
2886  struct in_addr ipaddr;
2887  int ip[4], ret = 0;
2888
2889  ret = sscanf (value, "%d.%d.%d.%d", &ip[0], &ip[1], &ip[2], &ip[3]);
2890
2891  if (ret != 4 || !inet_aton (value, &ipaddr))
2892    return FALSE;
2893  else
2894    return TRUE;
2895
2896}
2897
2898// note - network address returned in ipaddr
2899void
2900get_network (char *ipaddr, char *netmask)
2901{
2902  int ip[4], mask[4];
2903
2904  if (!ipaddr || !netmask)
2905    return;
2906
2907  sscanf (ipaddr, "%d.%d.%d.%d", &ip[0], &ip[1], &ip[2], &ip[3]);
2908  sscanf (netmask, "%d.%d.%d.%d", &mask[0], &mask[1], &mask[2], &mask[3]);
2909
2910  ip[0] &= mask[0];
2911  ip[1] &= mask[1];
2912  ip[2] &= mask[2];
2913  ip[3] &= mask[3];
2914
2915  sprintf (ipaddr, "%d.%d.%d.%d", ip[0], ip[1], ip[2], ip[3]);
2916#ifdef WDS_DEBUG
2917  fprintf (fp, "get_network return %s\n", ipaddr);
2918#endif
2919
2920}
2921
2922// note - broadcast addr returned in ipaddr
2923void
2924get_broadcast (char *ipaddr, char *netmask)
2925{
2926  int ip2[4], mask2[4];
2927  unsigned char ip[4], mask[4];
2928  if (!ipaddr || !netmask)
2929    return;
2930
2931  sscanf (ipaddr, "%d.%d.%d.%d", &ip2[0], &ip2[1], &ip2[2], &ip2[3]);
2932  sscanf (netmask, "%d.%d.%d.%d", &mask2[0], &mask2[1], &mask2[2], &mask2[3]);
2933  int i = 0;
2934  for (i = 0; i < 4; i++)
2935    {
2936      ip[i] = ip2[i];
2937      mask[i] = mask2[i];
2938//      ip[i] = (ip[i] & mask[i]) | !mask[i];
2939      ip[i] = (ip[i] & mask[i]) | (0xff & ~mask[i]);
2940    }
2941
2942  sprintf (ipaddr, "%d.%d.%d.%d", ip[0], ip[1], ip[2], ip[3]);
2943#ifdef WDS_DEBUG
2944  fprintf (fp, "get_broadcast return %s\n", value);
2945#endif
2946
2947}
2948
2949/* note: copied from Broadcom code and put in shared via this file */
2950
2951int
2952route_manip (int cmd, char *name, int metric, char *dst, char *gateway,
2953             char *genmask)
2954{
2955  int s;
2956  struct rtentry rt;
2957
2958  //dprintf("cmd=[%d] name=[%s] ipaddr=[%s] netmask=[%s] gateway=[%s] metric=[%d]\n",cmd,name,dst,genmask,gateway,metric);
2959
2960  /* Open a raw socket to the kernel */
2961  if ((s = socket (AF_INET, SOCK_DGRAM, 0)) < 0)
2962    goto err;
2963
2964  /* Fill in rtentry */
2965  memset (&rt, 0, sizeof (rt));
2966  if (dst)
2967    inet_aton (dst, &sin_addr (&rt.rt_dst));
2968  if (gateway)
2969    inet_aton (gateway, &sin_addr (&rt.rt_gateway));
2970  if (genmask)
2971    inet_aton (genmask, &sin_addr (&rt.rt_genmask));
2972  rt.rt_metric = metric;
2973  rt.rt_flags = RTF_UP;
2974  if (sin_addr (&rt.rt_gateway).s_addr)
2975    rt.rt_flags |= RTF_GATEWAY;
2976  if (sin_addr (&rt.rt_genmask).s_addr == INADDR_BROADCAST)
2977    rt.rt_flags |= RTF_HOST;
2978  rt.rt_dev = name;
2979
2980  /* Force address family to AF_INET */
2981  rt.rt_dst.sa_family = AF_INET;
2982  rt.rt_gateway.sa_family = AF_INET;
2983  rt.rt_genmask.sa_family = AF_INET;
2984
2985  if (ioctl (s, cmd, &rt) < 0)
2986    goto err;
2987
2988  close (s);
2989  return 0;
2990
2991err:
2992  close (s);
2993  perror (name);
2994  return errno;
2995}
2996
2997int
2998route_add (char *name, int metric, char *dst, char *gateway, char *genmask)
2999{
3000  return route_manip (SIOCADDRT, name, metric, dst, gateway, genmask);
3001}
3002
3003int
3004route_del (char *name, int metric, char *dst, char *gateway, char *genmask)
3005{
3006  return route_manip (SIOCDELRT, name, metric, dst, gateway, genmask);
3007}
3008
3009//#endif
3010
3011
3012#ifdef HAVE_MADWIFI
3013static char *stalist[] =
3014  { "ath0", "ath1", "ath2", "ath3", "ath4", "ath5", "ath6", "ath8", "ath9" };
3015char *
3016getSTA (void)
3017{
3018  int c = getifcount ("wifi");
3019  int i;
3020  for (i = 0; i < c; i++)
3021    {
3022      char mode[32];
3023      char netmode[32];
3024      sprintf (mode, "ath%d_mode", i);
3025      sprintf (netmode, "ath%d_net_mode", i);
3026      if (nvram_match (mode, "sta") && !nvram_match (netmode, "disabled"))
3027        {
3028          return stalist[i];
3029        }
3030
3031    }
3032  return NULL;
3033}
3034
3035char *
3036getWET (void)
3037{
3038  int c = getifcount ("wifi");
3039  int i;
3040  for (i = 0; i < c; i++)
3041    {
3042      char mode[32];
3043      char netmode[32];
3044      sprintf (mode, "ath%d_mode", i);
3045      sprintf (netmode, "ath%d_net_mode", i);
3046      if (nvram_match (mode, "wet") && !nvram_match (netmode, "disabled"))
3047        {
3048          return stalist[i];
3049        }
3050
3051    }
3052  return NULL;
3053}
3054#else
3055char *
3056getSTA ()
3057{
3058  int c = get_wl_instances ();
3059  int i;
3060  for (i = 0; i < c; i++)
3061    {
3062      if (nvram_nmatch ("sta","wl%d_mode", i) || nvram_nmatch ("apsta","wl%d_mode", i))
3063        {
3064         if (!nvram_nmatch ("disabled","wl%d_net_mode",i))
3065          return get_wl_instance_name(i);
3066         else
3067          return nvram_nget ("wl%d_ifname", i);
3068        }
3069
3070    }
3071  return NULL;
3072}
3073
3074char *
3075getWET ()
3076{
3077  int c = get_wl_instances ();
3078  int i;
3079  for (i = 0; i < c; i++)
3080    {
3081      if (nvram_nmatch ("wet","wl%d_mode", i) ||nvram_nmatch ("apstawet","wl%d_mode", i))
3082        {
3083         if (!nvram_nmatch ("disabled","wl%d_net_mode",i))
3084          return get_wl_instance_name(i);
3085         else
3086          return nvram_nget ("wl%d_ifname", i);
3087
3088        }
3089
3090    }
3091  return NULL;
3092}
3093
3094
3095#endif
3096
3097
3098int
3099ifexists (const char *ifname)
3100{
3101  return getifcount (ifname) > 0 ? 1 : 0;
3102}
3103
3104int
3105getifcount (const char *ifprefix)
3106{
3107/*  char devcall[128];
3108
3109  sprintf (devcall, "cat /proc/net/dev|grep \"%s\"|wc -l", ifprefix);
3110  FILE *in = popen (devcall, "rb");
3111  if (in == NULL)
3112    return 0;
3113  int count;
3114  fscanf (in, "%d", &count);
3115  pclose (in);
3116  return count;*/
3117  char *iflist = malloc (256);
3118  memset (iflist, 0, 256);
3119  int c = getIfList (iflist, ifprefix);
3120  free (iflist);
3121  return c;
3122}
3123
3124static void
3125skipline (FILE * in)
3126{
3127  while (1)
3128    {
3129      int c = getc (in);
3130      if (c == EOF)
3131        return;
3132      if (c == 0x0)
3133        return;
3134      if (c == 0xa)
3135        return;
3136    }
3137}
3138
3139//returns a physical interfacelist filtered by ifprefix. if ifprefix is NULL, all valid interfaces will be returned
3140int
3141getIfList (char *buffer, const char *ifprefix)
3142{
3143  FILE *in = fopen ("/proc/net/dev", "rb");
3144  char ifname[32];
3145//skip the first 2 lines
3146  skipline (in);
3147  skipline (in);
3148  int ifcount = 0;
3149  int count = 0;
3150  while (1)
3151    {
3152      int c = getc (in);
3153      if (c == EOF)
3154        {
3155          if (count)
3156            buffer[strlen (buffer) - 1] = 0;    //fixup last space
3157          fclose (in);
3158          return count;
3159        }
3160      if (c == 0)
3161        {
3162          if (count)
3163            buffer[strlen (buffer) - 1] = 0;    //fixup last space
3164          fclose (in);
3165          return count;
3166        }
3167      if (c == 0x20)
3168        continue;
3169      if (c == ':')
3170        {
3171          ifname[ifcount++] = 0;
3172          int skip = 0;
3173          if (ifprefix)
3174            {
3175              if (strncmp (ifname, ifprefix, strlen (ifprefix)))
3176                {
3177                  skip = 1;
3178                }
3179            }
3180          else
3181            {
3182              if (!strncmp (ifname, "wifi", 4))
3183                skip = 1;
3184              if (!strncmp (ifname, "imq", 3))
3185                skip = 1;
3186              if (!strncmp (ifname, "lo", 2))
3187                skip = 1;
3188              if (!strncmp (ifname, "teql", 4))
3189                skip = 1;
3190              if (!strncmp (ifname, "gre", 3))
3191                skip = 1;
3192              if (!strncmp (ifname, "ppp", 3))
3193                skip = 1;
3194              if (!strncmp (ifname, "tun", 3))
3195                skip = 1;
3196              if (!strncmp (ifname, "tap", 3))
3197                skip = 1;
3198            }
3199          if (!skip)
3200            {
3201              strcat (buffer, ifname);
3202              strcat (buffer, " ");
3203              count++;
3204            }
3205          skip = 0;
3206          ifcount = 0;
3207          memset (ifname, 0, 32);
3208          skipline (in);
3209          continue;
3210        }
3211      ifname[ifcount++] = c;
3212    }
3213}
3214
3215int
3216contains (const char *string, char value)
3217{
3218  if (string == NULL)
3219    return 0;
3220  int len = strlen (string);
3221  int i;
3222  for (i = 0; i < len; i++)
3223    {
3224      if (string[i] == value)
3225        return 1;
3226    }
3227  return 0;
3228}
3229
3230int
3231haswifi (void)
3232{
3233#ifdef HAVE_NOWIFI
3234  return 0;
3235#elif HAVE_MADWIFI
3236  return getifcount ("wifi") > 0 ? 1 : 0;
3237#else
3238  return 1;
3239#endif
3240}
3241
3242static uint32_t
3243str_to_addr (const char *addr)
3244{
3245  uint32_t split[4];
3246  uint32_t ip;
3247
3248  sscanf (addr, "%d.%d.%d.%d", &split[0], &split[1], &split[2], &split[3]);
3249
3250  ip = (split[0] << 24) | (split[1] << 16) | (split[2] << 8) | (split[3]);
3251
3252  return htonl (ip);
3253}
3254
3255void
3256getHostName (char *buf, char *ip)
3257{
3258  struct hostent *host;
3259  struct in_addr addr;
3260  res_init ();
3261  addr.s_addr = str_to_addr (ip);
3262  host = gethostbyaddr ((char *) &addr, 4, AF_INET);
3263  if (!host || !host->h_name)
3264    strcpy (buf, "unknown");
3265  else
3266    strcpy (buf, host->h_name);
3267}
3268
3269void
3270getinterfacelist (const char *ifprefix, char *buffer)
3271{
3272  int count = getifcount (ifprefix);
3273  int i;
3274  for (i = 0; i < count; i++)
3275    {
3276      char ifname[32];
3277      sprintf (ifname, "%s%d", ifprefix, i);
3278      strcat (buffer, ifname);
3279      if (i < count - 1)
3280        strcat (buffer, " ");
3281    }
3282}
3283
3284/*
3285 *     the following code was taken from:
3286 *
3287 *      Copyright (C) 2006 Jonathan Zarate
3288 *
3289 *      Licensed under GNU GPL v2 or later.     
3290 */
3291
3292int
3293f_exists (const char *path)     // note: anything but a directory
3294{
3295  struct stat st;
3296  return (stat (path, &st) == 0) && (!S_ISDIR (st.st_mode));
3297}
3298
3299int
3300f_read (const char *path, void *buffer, int max)
3301{
3302  int f;
3303  int n;
3304
3305  if ((f = open (path, O_RDONLY)) < 0)
3306    return -1;
3307  n = read (f, buffer, max);
3308  close (f);
3309  return n;
3310}
3311
3312
3313int
3314f_read_string (const char *path, char *buffer, int max)
3315{
3316  if (max <= 0)
3317    return -1;
3318  int n = f_read (path, buffer, max - 1);
3319  buffer[(n > 0) ? n : 0] = 0;
3320  return n;
3321}
3322
3323
3324int
3325wait_file_exists (const char *name, int max, int invert)
3326{
3327  while (max-- > 0)
3328    {
3329      if (f_exists (name) ^ invert)
3330        return 1;
3331      sleep (1);
3332    }
3333  return 0;
3334}
3335
3336char *
3337psname (int pid, char *buffer, int maxlen)
3338{
3339  char buf[512];
3340  char path[64];
3341  char *p;
3342
3343  if (maxlen <= 0)
3344    return NULL;
3345  *buffer = 0;
3346  sprintf (path, "/proc/%d/stat", pid);
3347  if ((f_read_string (path, buf, sizeof (buf)) > 4)
3348      && ((p = strrchr (buf, ')')) != NULL))
3349    {
3350      *p = 0;
3351      if (((p = strchr (buf, '(')) != NULL) && (atoi (buf) == pid))
3352        {
3353          strlcpy (buffer, p + 1, maxlen);
3354        }
3355    }
3356  return buffer;
3357}
3358
3359static int
3360_pidof (const char *name, pid_t ** pids)
3361{
3362  const char *p;
3363  char *e;
3364  DIR *dir;
3365  struct dirent *de;
3366  pid_t i;
3367  int count;
3368  char buf[256];
3369
3370  count = 0;
3371  *pids = NULL;
3372  if ((p = strchr (name, '/')) != NULL)
3373    name = p + 1;
3374  if ((dir = opendir ("/proc")) != NULL)
3375    {
3376      while ((de = readdir (dir)) != NULL)
3377        {
3378          i = strtol (de->d_name, &e, 10);
3379          if (*e != 0)
3380            continue;
3381          if (strcmp (name, psname (i, buf, sizeof (buf))) == 0)
3382            {
3383              if ((*pids =
3384                   realloc (*pids, sizeof (pid_t) * (count + 1))) == NULL)
3385                {
3386                  return -1;
3387                }
3388              (*pids)[count++] = i;
3389            }
3390        }
3391    }
3392  closedir (dir);
3393  return count;
3394}
3395
3396int
3397pidof (const char *name)
3398{
3399  pid_t *pids;
3400  pid_t p;
3401
3402  if (_pidof (name, &pids) > 0)
3403    {
3404      p = *pids;
3405      free (pids);
3406      return p;
3407    }
3408  return -1;
3409}
3410
3411int
3412killall (const char *name, int sig)
3413{
3414  pid_t *pids;
3415  int i;
3416  int r;
3417
3418  if ((i = _pidof (name, &pids)) > 0)
3419    {
3420      r = 0;
3421      do
3422        {
3423          r |= kill (pids[--i], sig);
3424        }
3425      while (i > 0);
3426      free (pids);
3427      return r;
3428    }
3429  return -2;
3430}
3431
3432int
3433isGrep (char *string, char *cmp)
3434{
3435  char devcall[128];
3436  int res;
3437  sprintf (devcall, "%s|grep \"%s\"|/bin/wc -l", string, cmp);
3438//system(devcall);
3439  FILE *in = popen (devcall, "rb");
3440  fscanf (in, "%d", &res);
3441  pclose (in);
3442  return res > 0 ? 1 : 0;
3443
3444}
3445
3446int
3447softkill (char *name)
3448{
3449  killall (name, SIGKILL);
3450  return 0;
3451}
3452static void
3453to64 (char *s, long v, int n)
3454{
3455
3456  unsigned char itoa64[] =
3457    "./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
3458
3459  while (--n >= 0)
3460    {
3461      *s++ = itoa64[v & 0x3f];
3462      v >>= 6;
3463    }
3464}
3465
3466char *
3467zencrypt (char *passwd)
3468{
3469  char salt[6];
3470  struct timeval tv;
3471  char *crypt (const char *, const char *);
3472
3473  gettimeofday (&tv, 0);
3474
3475  to64 (&salt[0], random (), 3);
3476  to64 (&salt[3], tv.tv_usec, 3);
3477  salt[5] = '\0';
3478
3479  return crypt (passwd, salt);
3480}
3481
3482void getLANMac (char *newmac)
3483{
3484        strcpy (newmac, nvram_safe_get ("et0macaddr"));
3485 
3486        if (nvram_match ("port_swap", "1"))
3487                {
3488                if (strlen(nvram_safe_get ("et1macaddr")) != 0) //safe: maybe et1macaddr not there?
3489                        {
3490                        strcpy (newmac, nvram_safe_get ("et1macaddr"));
3491                        }
3492                else
3493                        {
3494                        MAC_ADD(newmac);  //et0macaddr +1
3495                        }
3496                }
3497       
3498        return;
3499}
3500
3501void getWirelessMac (char *newmac)
3502{
3503//      if (strlen(nvram_safe_get ("il0macaddr")) != 0)
3504//              {
3505//              strcpy (newmac, nvram_safe_get ("il0macaddr"));
3506//              }
3507//      else
3508                {
3509                if (nvram_match ("port_swap", "1"))
3510                        {
3511                        if (strlen(nvram_safe_get ("et1macaddr")) != 0) //safe: maybe et1macaddr not there?
3512                                {
3513                                strcpy (newmac, nvram_safe_get ("et1macaddr"));
3514                                MAC_ADD (newmac);  //et1macaddr +2
3515                                MAC_ADD (newmac);               
3516                                }
3517                        else
3518                                {
3519                                strcpy (newmac, nvram_safe_get ("et0macaddr"));
3520                                MAC_ADD (newmac);  //et0macaddr +3
3521                                MAC_ADD (newmac);
3522                                MAC_ADD (newmac);                               
3523                                }
3524                        }
3525                else
3526                        {
3527                        strcpy (newmac, nvram_safe_get ("et0macaddr"));
3528                        MAC_ADD (newmac);  //et0macaddr +2
3529                        MAC_ADD (newmac);
3530                        }
3531                }
3532       
3533        return;         
3534}
3535
3536void getWANMac (char *newmac)
3537{
3538        strcpy (newmac, nvram_safe_get ("et0macaddr"));
3539        MAC_ADD (newmac);  //et0macaddr +1
3540 
3541        if (nvram_match ("port_swap", "1"))
3542                {
3543                if (strlen(nvram_safe_get ("et1macaddr")) != 0) //safe: maybe et1macaddr not there?
3544                        {
3545                        strcpy (newmac, nvram_safe_get ("et1macaddr"));
3546                        MAC_ADD (newmac);  //et1macaddr +1                     
3547                        }
3548                else
3549                        {
3550                        MAC_ADD (newmac);  //et0macaddr +2
3551                        }
3552                }
3553       
3554        return;
3555}
3556
3557#ifdef HAVE_AQOS
3558
3559static char *
3560get_wshaper_dev (void)
3561{
3562  if (nvram_match ("wshaper_dev", "WAN"))
3563    return get_wan_face ();
3564  else
3565    return "br0";
3566}
3567
3568void
3569add_userip (char *ip, int idx, char *upstream, char *downstream)
3570{
3571  int base = 120 + idx;
3572  char up[32];
3573  char down[32];
3574  char ups[32];
3575  char downs[32];
3576  sprintf (up, "1:%d", base);
3577  sprintf (down, "1:%d", base + 1);
3578  sprintf (ups, "%skbit", upstream);
3579  sprintf (downs, "%skbit", downstream);
3580  if (nvram_match ("qos_type", "0"))
3581    {
3582      eval ("tc", "class", "add", "dev", get_wshaper_dev (), "parent", "1:",
3583            "classid", up, "htb", "rate", ups, "ceil", ups);
3584      eval ("tc", "filter", "add", "dev", get_wshaper_dev (), "parent", "1:",
3585            "protocol", "ip", "prio", "1", "u32", "match", "ip", "src", ip,
3586            "flowid", up);
3587      eval ("tc", "class", "add", "dev", "imq0", "parent", "1:", "classid",
3588            down, "htb", "rate", downs, "ceil", downs);
3589      eval ("tc", "filter", "add", "dev", "imq0", "parent", "1:", "protocol",
3590            "ip", "prio", "1", "u32", "match", "ip", "dst", ip, "flowid",
3591            down);
3592    }
3593  else
3594    {
3595      eval ("tc", "class", "add", "dev", get_wshaper_dev (), "parent", "1:",
3596            "classid", up, "htb", "rate", ups, "ceil", ups);
3597      eval ("tc", "filter", "add", "dev", get_wshaper_dev (), "parent", "1:",
3598            "protocol", "ip", "prio", "1", "u32", "match", "ip", "src", ip,
3599            "flowid", up);
3600      eval ("tc", "class", "add", "dev", "imq0", "parent", "1:", "classid",
3601            down, "htb", "rate", downs, "ceil", downs);
3602      eval ("tc", "filter", "add", "dev", "imq0", "parent", "1:", "protocol",
3603            "ip", "prio", "1", "u32", "match", "ip", "dst", ip, "flowid",
3604            down);
3605    }
3606
3607}
3608
3609void
3610add_usermac (char *mac, int idx, char *upstream, char *downstream)
3611{
3612  unsigned char octet[6];
3613  ether_atoe (mac, octet);
3614
3615  int base = 120 + idx;
3616  char up[32];
3617  char down[32];
3618  char ups[32];
3619  char downs[32];
3620  char oct2[32];
3621  char oct4[32];
3622  char doct2[32];
3623  char doct4[32];
3624  sprintf (up, "1:%d", base);
3625  sprintf (down, "1:%d", base + 1);
3626  sprintf (ups, "%skbit", upstream);
3627  sprintf (downs, "%skbit", downstream);
3628
3629  sprintf (oct2, "%X%X", octet[4], octet[5]);
3630  sprintf (oct4, "%X%X%X%X", octet[0], octet[1], octet[2], octet[3]);
3631
3632  sprintf (doct4, "%X%X%X%X", octet[2], octet[3], octet[4], octet[5]);
3633  sprintf (doct2, "%X%X", octet[0], octet[1]);
3634
3635  if (nvram_match ("qos_type", "0"))
3636    {
3637      eval ("tc", "class", "add", "dev", get_wshaper_dev (), "parent", "1:",
3638            "classid", up, "htb", "rate", ups, "ceil", ups);
3639      eval ("tc", "filter", "add", "dev", get_wshaper_dev (), "parent", "1:",
3640            "protocol", "ip", "prio", "1", "u32", "match", "u16", "0x0800",
3641            "0xFFFF", "at", "-2", "match", "u16", oct2, "0xFFFF", "at", "-4",
3642            "match", "u32", oct4, "0xFFFFFFFF", "at", "-8", "flowid", up);
3643      eval ("tc", "class", "add", "dev", "imq0", "parent", "1:", "classid",
3644            down, "htb", "rate", downs, "ceil", downs);
3645      eval ("tc", "filter", "add", "dev", "imq0", "parent", "1:", "protocol",
3646            "ip", "prio", "1", "u32", "match", "u16", "0x0800", "0xFFFF",
3647            "at", "-2", "match", "u32", doct4, "0xFFFFFFFF", "at", "-12",
3648            "match", "u16", doct2, "0xFFFF", "at", "-14", "flowid", down);
3649    }
3650  else
3651    {
3652      eval ("tc", "class", "add", "dev", get_wshaper_dev (), "parent", "1:",
3653            "classid", up, "htb", "rate", ups, "ceil", ups);
3654      eval ("tc", "filter", "add", "dev", get_wshaper_dev (), "parent", "1:",
3655            "protocol", "ip", "prio", "1", "u32", "match", "u16", "0x0800",
3656            "0xFFFF", "at", "-2", "match", "u16", oct2, "0xFFFF", "at", "-4",
3657            "match", "u32", oct4, "0xFFFFFFFF", "at", "-8", "flowid", up);
3658      eval ("tc", "class", "add", "dev", "imq0", "parent", "1:", "classid",
3659            down, "htb", "rate", downs, "ceil", downs);
3660      eval ("tc", "filter", "add", "dev", "imq0", "parent", "1:", "protocol",
3661            "ip", "prio", "1", "u32", "match", "u16", "0x0800", "0xFFFF",
3662            "at", "-2", "match", "u32", doct4, "0xFFFFFFFF", "at", "-12",
3663            "match", "u16", doct2, "0xFFFF", "at", "-14", "flowid", down);
3664    }
3665
3666}
3667
3668
3669#endif
3670
3671
3672
3673#ifdef HAVE_X86
3674
3675static int fd;
3676
3677void
3678SetEnvironment ()
3679{
3680  system ("stty ispeed 2400 < /dev/tts/1");
3681  system ("stty raw < /dev/tts/1");
3682}
3683
3684int Cmd = 254;                  /* EZIO Command */
3685int cls = 1;                    /* Clear screen */
3686void
3687Cls ()
3688{
3689  write (fd, &Cmd, 1);
3690  write (fd, &cls, 1);
3691}
3692
3693int init = 0x28;
3694void
3695Init ()
3696{
3697  write (fd, &Cmd, 1);
3698  write (fd, &init, 1);
3699}
3700
3701int stopsend = 0x37;
3702void
3703StopSend ()
3704{
3705  write (fd, &Cmd, 1);
3706  write (fd, &init, 1);
3707}
3708
3709int home = 2;                   /* Home cursor */
3710void
3711Home ()
3712{
3713  write (fd, &Cmd, 1);
3714  write (fd, &home, 1);
3715}
3716
3717int readkey = 6;                /* Read key */
3718void
3719ReadKey ()
3720{
3721  write (fd, &Cmd, 1);
3722  write (fd, &readkey, 1);
3723}
3724
3725int blank = 8;                  /* Blank display */
3726void
3727Blank ()
3728{
3729  write (fd, &Cmd, 1);
3730  write (fd, &blank, 1);
3731}
3732
3733int hide = 12;                  /* Hide cursor & display blanked characters */
3734void
3735Hide ()
3736{
3737  write (fd, &Cmd, 1);
3738  write (fd, &hide, 1);
3739}
3740
3741int turn = 13;                  /* Turn On (blinking block cursor) */
3742void
3743TurnOn ()
3744{
3745  write (fd, &Cmd, 1);
3746  write (fd, &turn, 1);
3747}
3748
3749int show = 14;                  /* Show underline cursor */
3750void
3751Show ()
3752{
3753  write (fd, &Cmd, 1);
3754  write (fd, &show, 1);
3755}
3756
3757int movel = 16;                 /* Move cursor 1 character left */
3758void
3759MoveL ()
3760{
3761  write (fd, &Cmd, 1);
3762  write (fd, &movel, 1);
3763}
3764
3765int mover = 20;                 /* Move cursor 1 character right */
3766void
3767MoveR ()
3768{
3769  write (fd, &Cmd, 1);
3770  write (fd, &mover, 1);
3771}
3772
3773int scl = 24;                   /* Scroll cursor 1 character left */
3774void
3775ScrollL ()
3776{
3777  write (fd, &Cmd, 1);
3778  write (fd, &scl, 1);
3779}
3780
3781int scr = 28;                   /* Scroll cursor 1 character right */
3782void
3783ScrollR ()
3784{
3785  write (fd, &Cmd, 1);
3786  write (fd, &scr, 1);
3787}
3788
3789int setdis = 64;                /* Command */
3790void
3791SetDis ()
3792{
3793  write (fd, &Cmd, 1);
3794  write (fd, &setdis, 1);
3795
3796}
3797
3798
3799int a, b;
3800void
3801ShowMessage (char *str1, char *str2)
3802{
3803  char nul[] = "                                       ";
3804  a = strlen (str1);
3805  b = 40 - a;
3806  write (fd, str1, a);
3807  write (fd, nul, b);
3808  write (fd, str2, strlen (str2));
3809}
3810
3811void
3812initlcd ()
3813{
3814
3815  fd = open ("/dev/tts/1", O_RDWR);
3816                                  /** Open Serial port (COM2) */
3817  if (fd > 0)
3818    {
3819      close (fd);
3820      SetEnvironment ();        /* Set RAW mode */
3821      fd = open ("/dev/tts/1", O_RDWR);
3822      Init ();                  /* Initialize EZIO twice */
3823      Init ();
3824
3825      Cls ();                   /* Clear screen */
3826    }
3827  close (fd);
3828}
3829
3830void
3831lcdmessage (char *message)
3832{
3833  fd = open ("/dev/tts/1", O_RDWR);/** Open Serial port (COM2) */
3834
3835  if (fd > 0)
3836    {
3837      Init ();                  /* Initialize EZIO twice */
3838      Init ();
3839      SetDis ();
3840      Cls ();
3841      Home ();
3842      ShowMessage ("State", message);
3843      close (fd);
3844    }
3845}
3846void
3847lcdmessaged (char *dual, char *message)
3848{
3849
3850  fd = open ("/dev/tts/1", O_RDWR);
3851                                  /** Open Serial port (COM2) */
3852
3853  if (fd > 0)
3854    {
3855      Init ();                  /* Initialize EZIO twice */
3856      Init ();
3857      SetDis ();
3858      Cls ();                   /* Clear screen */
3859      Home ();
3860      ShowMessage (dual, message);
3861      close (fd);
3862    }
3863}
3864
3865
3866#endif
3867
3868
Note: See TracBrowser for help on using the repository browser.