11573Srgrimes/* 21573Srgrimes * Copyright (c) 1987, 1993 31573Srgrimes * The Regents of the University of California. All rights reserved. 41573Srgrimes * 51573Srgrimes * Redistribution and use in source and binary forms, with or without 61573Srgrimes * modification, are permitted provided that the following conditions 71573Srgrimes * are met: 81573Srgrimes * 1. Redistributions of source code must retain the above copyright 91573Srgrimes * notice, this list of conditions and the following disclaimer. 101573Srgrimes * 2. Redistributions in binary form must reproduce the above copyright 111573Srgrimes * notice, this list of conditions and the following disclaimer in the 121573Srgrimes * documentation and/or other materials provided with the distribution. 131573Srgrimes * 4. Neither the name of the University nor the names of its contributors 141573Srgrimes * may be used to endorse or promote products derived from this software 151573Srgrimes * without specific prior written permission. 161573Srgrimes * 171573Srgrimes * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 181573Srgrimes * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 191573Srgrimes * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 201573Srgrimes * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 211573Srgrimes * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 221573Srgrimes * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 231573Srgrimes * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 241573Srgrimes * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 251573Srgrimes * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 261573Srgrimes * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 271573Srgrimes * SUCH DAMAGE. 281573Srgrimes */ 291573Srgrimes 301573Srgrimes#if defined(LIBC_SCCS) && !defined(lint) 311573Srgrimesstatic char sccsid[] = "@(#)timezone.c 8.1 (Berkeley) 6/4/93"; 321573Srgrimes#endif /* LIBC_SCCS and not lint */ 3390041Sobrien#include <sys/cdefs.h> 3490041Sobrien__FBSDID("$FreeBSD$"); 351573Srgrimes 361573Srgrimes#include <sys/types.h> 371573Srgrimes#include <sys/time.h> 381573Srgrimes#include <stdio.h> 391573Srgrimes#include <stdlib.h> 401573Srgrimes#include <string.h> 419935Swollman#define TZ_MAX_CHARS 255 421573Srgrimes 43200150Sedchar *_tztab(int, int); 441573Srgrimes 451573Srgrimes/* 461573Srgrimes * timezone -- 471573Srgrimes * The arguments are the number of minutes of time you are westward 481573Srgrimes * from Greenwich and whether DST is in effect. It returns a string 491573Srgrimes * giving the name of the local timezone. Should be replaced, in the 501573Srgrimes * application code, by a call to localtime. 511573Srgrimes */ 521573Srgrimes 531573Srgrimesstatic char czone[TZ_MAX_CHARS]; /* space for zone name */ 541573Srgrimes 551573Srgrimeschar * 56200150Sedtimezone(int zone, int dst) 571573Srgrimes{ 5890041Sobrien char *beg, 591573Srgrimes *end; 601573Srgrimes 6117141Sjkh if ( (beg = getenv("TZNAME")) ) { /* set in environment */ 6217141Sjkh if ( (end = index(beg, ',')) ) {/* "PST,PDT" */ 631573Srgrimes if (dst) 641573Srgrimes return(++end); 651573Srgrimes *end = '\0'; 661573Srgrimes (void)strncpy(czone,beg,sizeof(czone) - 1); 671573Srgrimes czone[sizeof(czone) - 1] = '\0'; 681573Srgrimes *end = ','; 691573Srgrimes return(czone); 701573Srgrimes } 711573Srgrimes return(beg); 721573Srgrimes } 731573Srgrimes return(_tztab(zone,dst)); /* default: table or created zone */ 741573Srgrimes} 751573Srgrimes 761573Srgrimesstatic struct zone { 771573Srgrimes int offset; 781573Srgrimes char *stdzone; 791573Srgrimes char *dlzone; 801573Srgrimes} zonetab[] = { 8117141Sjkh {-1*60, "MET", "MET DST"}, /* Middle European */ 8217141Sjkh {-2*60, "EET", "EET DST"}, /* Eastern European */ 8317141Sjkh {4*60, "AST", "ADT"}, /* Atlantic */ 8417141Sjkh {5*60, "EST", "EDT"}, /* Eastern */ 8517141Sjkh {6*60, "CST", "CDT"}, /* Central */ 8617141Sjkh {7*60, "MST", "MDT"}, /* Mountain */ 8717141Sjkh {8*60, "PST", "PDT"}, /* Pacific */ 881573Srgrimes#ifdef notdef 891573Srgrimes /* there's no way to distinguish this from WET */ 9017141Sjkh {0, "GMT", 0}, /* Greenwich */ 911573Srgrimes#endif 9217141Sjkh {0*60, "WET", "WET DST"}, /* Western European */ 9317141Sjkh {-10*60,"EST", "EST"}, /* Aust: Eastern */ 9417141Sjkh {-10*60+30,"CST", "CST"}, /* Aust: Central */ 9517141Sjkh {-8*60, "WST", 0}, /* Aust: Western */ 9617141Sjkh {-1} 971573Srgrimes}; 981573Srgrimes 991573Srgrimes/* 1001573Srgrimes * _tztab -- 1011573Srgrimes * check static tables or create a new zone name; broken out so that 1021573Srgrimes * we can make a guess as to what the zone is if the standard tables 1031573Srgrimes * aren't in place in /etc. DO NOT USE THIS ROUTINE OUTSIDE OF THE 1041573Srgrimes * STANDARD LIBRARY. 1051573Srgrimes */ 1061573Srgrimeschar * 107200150Sed_tztab(int zone, int dst) 1081573Srgrimes{ 10990041Sobrien struct zone *zp; 11090041Sobrien char sign; 1111573Srgrimes 1121573Srgrimes for (zp = zonetab; zp->offset != -1;++zp) /* static tables */ 1131573Srgrimes if (zp->offset == zone) { 1141573Srgrimes if (dst && zp->dlzone) 1151573Srgrimes return(zp->dlzone); 1161573Srgrimes if (!dst && zp->stdzone) 1171573Srgrimes return(zp->stdzone); 1181573Srgrimes } 1191573Srgrimes 1201573Srgrimes if (zone < 0) { /* create one */ 1211573Srgrimes zone = -zone; 1221573Srgrimes sign = '+'; 1231573Srgrimes } 1241573Srgrimes else 1251573Srgrimes sign = '-'; 12632687Simp (void)snprintf(czone, sizeof(czone), 12732687Simp "GMT%c%d:%02d",sign,zone / 60,zone % 60); 1281573Srgrimes return(czone); 1291573Srgrimes} 130