FreeCalypso > hg > freecalypso-sw
annotate miscutil/imei-luhn.c @ 462:6500e1817d9b
doc/Roadmap: written
author | Michael Spacefalcon <msokolov@ivan.Harhan.ORG> |
---|---|
date | Mon, 23 Jun 2014 20:39:36 +0000 |
parents | cd043e690621 |
children |
rev | line source |
---|---|
271
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
1 /* |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
2 * This program computes the Luhn check digit for an IMEI number given |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
3 * the first 14 digits, or verifies the correctness of this check digit |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
4 * given a 15-digit number as input. |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
5 * |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
6 * The number given on the command line may optionally include punctuation, |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
7 * which is skipped and ignored. |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
8 */ |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
9 |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
10 #include <stdio.h> |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
11 #include <ctype.h> |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
12 #include <stdlib.h> |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
13 |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
14 char digits[15]; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
15 |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
16 compute_cd() |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
17 { |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
18 int i, dig, sum; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
19 |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
20 sum = 0; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
21 for (i = 0; i < 14; i++) { |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
22 dig = digits[i]; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
23 if (i & 1) { |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
24 dig *= 2; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
25 if (dig > 9) |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
26 dig -= 9; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
27 } |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
28 sum += dig; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
29 } |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
30 dig = sum % 10; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
31 if (dig) |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
32 dig = 10 - dig; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
33 return dig; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
34 } |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
35 |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
36 main(argc, argv) |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
37 char **argv; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
38 { |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
39 char *cp; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
40 int i; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
41 |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
42 if (argc != 2) { |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
43 usage: fprintf(stderr, "usage: %s number\n", argv[0]); |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
44 exit(2); |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
45 } |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
46 cp = argv[1]; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
47 if (!isdigit(*cp)) |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
48 goto usage; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
49 for (i = 0; *cp; ) { |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
50 if (ispunct(*cp)) |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
51 cp++; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
52 if (!isdigit(*cp)) |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
53 goto usage; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
54 if (i >= 15) { |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
55 wrong_len: fprintf(stderr, |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
56 "error: argument must have 14 or 15 digits\n"); |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
57 exit(2); |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
58 } |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
59 digits[i++] = *cp++ - '0'; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
60 } |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
61 switch (i) { |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
62 case 14: |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
63 printf("%d\n", compute_cd()); |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
64 exit(0); |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
65 case 15: |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
66 if (digits[14] == compute_cd()) { |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
67 printf("IMEI OK\n"); |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
68 exit(0); |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
69 } else { |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
70 printf("Check digit mismatch!\n"); |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
71 exit(1); |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
72 } |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
73 default: |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
74 goto wrong_len; |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
75 } |
cd043e690621
imei-luhn utility written
Michael Spacefalcon <msokolov@ivan.Harhan.ORG>
parents:
diff
changeset
|
76 } |