1 : /*
2 : * Copyright 2009 The Native Client Authors. All rights reserved.
3 : * Use of this source code is governed by a BSD-style license that can
4 : * be found in the LICENSE file.
5 : */
6 :
7 : /*
8 : * Some useful routines to handle command line arguments.
9 : */
10 :
11 : #include <stdlib.h>
12 : #include <string.h>
13 :
14 : #include "native_client/src/shared/utils/flags.h"
15 :
16 : /*
17 : * Given a pointer to a flag name to be
18 : * checked against the pointer to the corresponding
19 : * argument, return true iff the argument begins with
20 : * the flag name. During the match, advance both pointers
21 : * to the maximal matched prefix.
22 : */
23 : static Bool MatchFlagPrefix(const char** name,
24 13926 : const char** arg) {
25 55231 : while (*(*name)) {
26 40157 : if (*(*name) != *(*arg)) {
27 12778 : return FALSE;
28 : }
29 27379 : ++(*name);
30 27379 : ++(*arg);
31 : }
32 1148 : return TRUE;
33 : }
34 :
35 : /*
36 : * Given a pointer to a flag name to be checked
37 : * against the pointer to the corresponding argument, return true
38 : * iff the argument begins with the flag name, followed by
39 : * and equals sign. During the match, advance both pointers
40 : * to the maximal matched prefix.
41 : */
42 : static Bool MatchFlagPrefixEquals(const char** name,
43 13352 : const char** arg) {
44 13352 : const char* equals = "=";
45 13352 : return MatchFlagPrefix(name, arg) &&
46 : MatchFlagPrefix(&equals, arg);
47 : }
48 :
49 : Bool GrokBoolFlag(const char* name,
50 : const char* arg,
51 11270 : Bool* flag) {
52 11270 : if (strcmp(name, arg) == 0) {
53 145 : *flag = TRUE;
54 145 : return TRUE;
55 11125 : } else if (MatchFlagPrefixEquals(&name, &arg)) {
56 51 : if (strcmp(arg, "true") == 0) {
57 0 : *flag = TRUE;
58 0 : return TRUE;
59 51 : } else if (strcmp(arg, "false") == 0) {
60 51 : *flag = FALSE;
61 51 : return TRUE;
62 : }
63 : }
64 11074 : return FALSE;
65 : }
66 :
67 0 : static Bool IsZero(const char* arg) {
68 0 : while (*arg) {
69 0 : if ('0' != *arg) {
70 0 : return FALSE;
71 : }
72 0 : ++arg;
73 : }
74 0 : return TRUE;
75 : }
76 :
77 : Bool GrokIntFlag(const char* name,
78 : const char* arg,
79 582 : int* flag) {
80 582 : if (MatchFlagPrefixEquals(&name, &arg)) {
81 125 : int value = atoi(arg);
82 : /* verify that arg is all zeros. Otherwise,
83 : * assume that 0 was returned due to an error.
84 : */
85 125 : if (0 == value && !IsZero(arg)) return FALSE;
86 125 : *flag = value;
87 125 : return TRUE;
88 : }
89 457 : return FALSE;
90 : }
91 :
92 : Bool GrokUint32HexFlag(const char* name,
93 : const char* arg,
94 424 : uint32_t* flag) {
95 424 : if (MatchFlagPrefixEquals(&name, &arg)) {
96 2 : unsigned long value = strtoul(arg, NULL, 16);
97 : /* Verify that arg is all zeros. Otherwise,
98 : * assume that 0 was returned due to an error.
99 : */
100 2 : if (0L == value && !IsZero(arg)) return FALSE;
101 2 : *flag = (uint32_t) value;
102 2 : return TRUE;
103 : }
104 422 : return FALSE;
105 : }
106 :
107 :
108 : Bool GrokCstringFlag(const char* name,
109 : const char* arg,
110 1221 : char** flag) {
111 1221 : if (MatchFlagPrefixEquals(&name, &arg)) {
112 396 : *flag = (char*) arg;
113 396 : return TRUE;
114 : }
115 825 : return FALSE;
116 : }
|