123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322 |
- /*
- * This file is part of the UCB release of Plan 9. It is subject to the license
- * terms in the LICENSE file found in the top-level directory of this
- * distribution and at http://akaros.cs.berkeley.edu/files/Plan9License. No
- * part of the UCB release of Plan 9, including this file, may be copied,
- * modified, propagated, or distributed except according to the terms contained
- * in the LICENSE file.
- */
- #include <u.h>
- #include <libc.h>
- #include <bio.h>
- char dayw[] =
- {
- " S M Tu W Th F S"
- };
- char *smon[] =
- {
- "January", "February", "March", "April",
- "May", "June", "July", "August",
- "September", "October", "November", "December",
- };
- char mon[] =
- {
- 0,
- 31, 29, 31, 30,
- 31, 30, 31, 31,
- 30, 31, 30, 31,
- };
- char string[432];
- Biobuf bout;
- void main(int argc, char *argv[]);
- int number(char *str);
- void pstr(char *str, int n);
- void cal(int m, int y, char *p, int w);
- int jan1(int yr);
- int curmo(void);
- int curyr(void);
- void
- main(int argc, char *argv[])
- {
- int y, i, j, m;
- if(argc > 3) {
- fprint(2, "usage: cal [month] [year]\n");
- exits("usage");
- }
- Binit(&bout, 1, OWRITE);
- /*
- * no arg, print current month
- */
- if(argc == 1) {
- m = curmo();
- y = curyr();
- goto xshort;
- }
- /*
- * one arg
- * if looks like a month, print month
- * else print year
- */
- if(argc == 2) {
- y = number(argv[1]);
- if(y < 0)
- y = -y;
- if(y >= 1 && y <= 12) {
- m = y;
- y = curyr();
- goto xshort;
- }
- goto xint32_t;
- }
- /*
- * two arg, month and year
- */
- m = number(argv[1]);
- if(m < 0)
- m = -m;
- y = number(argv[2]);
- goto xshort;
- /*
- * print out just month
- */
- xshort:
- if(m < 1 || m > 12)
- goto badarg;
- if(y < 1 || y > 9999)
- goto badarg;
- Bprint(&bout, " %s %ud\n", smon[m-1], y);
- Bprint(&bout, "%s\n", dayw);
- cal(m, y, string, 24);
- for(i=0; i<6*24; i+=24)
- pstr(string+i, 24);
- exits(0);
- /*
- * print out complete year
- */
- xint32_t:
- y = number(argv[1]);
- if(y<1 || y>9999)
- goto badarg;
- Bprint(&bout, "\n\n\n");
- Bprint(&bout, " %ud\n", y);
- Bprint(&bout, "\n");
- for(i=0; i<12; i+=3) {
- for(j=0; j<6*72; j++)
- string[j] = '\0';
- Bprint(&bout, " %.3s", smon[i]);
- Bprint(&bout, " %.3s", smon[i+1]);
- Bprint(&bout, " %.3s\n", smon[i+2]);
- Bprint(&bout, "%s %s %s\n", dayw, dayw, dayw);
- cal(i+1, y, string, 72);
- cal(i+2, y, string+23, 72);
- cal(i+3, y, string+46, 72);
- for(j=0; j<6*72; j+=72)
- pstr(string+j, 72);
- }
- Bprint(&bout, "\n\n\n");
- exits(0);
- badarg:
- Bprint(&bout, "cal: bad argument\n");
- }
- struct
- {
- char* word;
- int val;
- } dict[] =
- {
- "jan", 1,
- "january", 1,
- "feb", 2,
- "february", 2,
- "mar", 3,
- "march", 3,
- "apr", 4,
- "april", 4,
- "may", 5,
- "jun", 6,
- "june", 6,
- "jul", 7,
- "july", 7,
- "aug", 8,
- "august", 8,
- "sep", 9,
- "sept", 9,
- "september", 9,
- "oct", 10,
- "october", 10,
- "nov", 11,
- "november", 11,
- "dec", 12,
- "december", 12,
- 0
- };
- /*
- * convert to a number.
- * if its a dictionary word,
- * return negative number
- */
- int
- number(char *str)
- {
- int n, c;
- char *s;
- for(n=0; s=dict[n].word; n++)
- if(strcmp(s, str) == 0)
- return -dict[n].val;
- n = 0;
- s = str;
- while(c = *s++) {
- if(c<'0' || c>'9')
- return 0;
- n = n*10 + c-'0';
- }
- return n;
- }
- void
- pstr(char *str, int n)
- {
- int i;
- char *s;
- s = str;
- i = n;
- while(i--)
- if(*s++ == '\0')
- s[-1] = ' ';
- i = n+1;
- while(i--)
- if(*--s != ' ')
- break;
- s[1] = '\0';
- Bprint(&bout, "%s\n", str);
- }
- void
- cal(int m, int y, char *p, int w)
- {
- int d, i;
- char *s;
- s = p;
- d = jan1(y);
- mon[2] = 29;
- mon[9] = 30;
- switch((jan1(y+1)+7-d)%7) {
- /*
- * non-leap year
- */
- case 1:
- mon[2] = 28;
- break;
- /*
- * 1752
- */
- default:
- mon[9] = 19;
- break;
- /*
- * leap year
- */
- case 2:
- ;
- }
- for(i=1; i<m; i++)
- d += mon[i];
- d %= 7;
- s += 3*d;
- for(i=1; i<=mon[m]; i++) {
- if(i==3 && mon[m]==19) {
- i += 11;
- mon[m] += 11;
- }
- if(i > 9)
- *s = i/10+'0';
- s++;
- *s++ = i%10+'0';
- s++;
- if(++d == 7) {
- d = 0;
- s = p+w;
- p = s;
- }
- }
- }
- /*
- * return day of the week
- * of jan 1 of given year
- */
- int
- jan1(int yr)
- {
- int y, d;
- /*
- * normal gregorian calendar
- * one extra day per four years
- */
- y = yr;
- d = 4+y+(y+3)/4;
- /*
- * julian calendar
- * regular gregorian
- * less three days per 400
- */
- if(y > 1800) {
- d -= (y-1701)/100;
- d += (y-1601)/400;
- }
- /*
- * great calendar changeover instant
- */
- if(y > 1752)
- d += 3;
- return d%7;
- }
- /*
- * system dependent
- * get current month and year
- */
- int
- curmo(void)
- {
- Tm *tm;
- tm = localtime(time(0));
- return tm->mon+1;
- }
- int
- curyr(void)
- {
- Tm *tm;
- tm = localtime(time(0));
- return tm->year+1900;
- }
|