mirror of
https://frontier.innolan.net/rainlance/amiga-tz.git
synced 2025-11-21 10:03:45 +00:00
365 lines
8.1 KiB
C
365 lines
8.1 KiB
C
/*
|
|
* Copyright (c) 2015 Carsten Larsen
|
|
* All rights reserved.
|
|
*
|
|
* Redistribution and use in source and binary forms, with or without
|
|
* modification, are permitted provided that the following conditions
|
|
* are met:
|
|
* 1. Redistributions of source code must retain the above copyright
|
|
* notice, this list of conditions and the following disclaimer.
|
|
* 2. Redistributions in binary form must reproduce the above copyright
|
|
* notice, this list of conditions and the following disclaimer in the
|
|
* documentation and/or other materials provided with the distribution.
|
|
*
|
|
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
|
|
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
|
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
|
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
|
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
|
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
|
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
|
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
|
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
*
|
|
*/
|
|
|
|
#include "amiga_tz.h"
|
|
#include "private.h"
|
|
|
|
#ifdef AOS3
|
|
/**********************************************************************/
|
|
struct Library* ctypeBase = NULL;
|
|
struct Locale* ctypeLocale = NULL;
|
|
/**********************************************************************/
|
|
void InitCTypeLocale()
|
|
{
|
|
ctypeBase = OpenLibrary(LOCALELIB_NAME, LOCALELIB_REV);
|
|
ctypeLocale = OpenLocale(NULL);
|
|
}
|
|
|
|
void CleanupCTypeLocale()
|
|
{
|
|
if (ctypeBase != NULL) {
|
|
CloseLocale(ctypeLocale);
|
|
ctypeLocale = NULL;
|
|
CloseLibrary(ctypeBase);
|
|
ctypeBase = NULL;
|
|
}
|
|
}
|
|
/**********************************************************************/
|
|
int isalnum(int c)
|
|
{
|
|
int res;
|
|
InitCTypeLocale();
|
|
res = IsAlNum(ctypeLocale, (ULONG)c);
|
|
CleanupCTypeLocale();
|
|
return res;
|
|
}
|
|
|
|
int isalpha(int c)
|
|
{
|
|
int res;
|
|
InitCTypeLocale();
|
|
res = IsAlpha(ctypeLocale, (ULONG)c);
|
|
CleanupCTypeLocale();
|
|
return res;
|
|
}
|
|
|
|
int isdigit(int c)
|
|
{
|
|
int res;
|
|
InitCTypeLocale();
|
|
res = IsDigit(ctypeLocale, (ULONG)c);
|
|
CleanupCTypeLocale();
|
|
return res;
|
|
}
|
|
|
|
int ispunct(int c)
|
|
{
|
|
int res;
|
|
InitCTypeLocale();
|
|
res = IsPunct(ctypeLocale, (ULONG)c);
|
|
CleanupCTypeLocale();
|
|
return res;
|
|
}
|
|
|
|
int isspace(int c)
|
|
{
|
|
int res;
|
|
InitCTypeLocale();
|
|
res = IsSpace(ctypeLocale, (ULONG)c);
|
|
CleanupCTypeLocale();
|
|
return res;
|
|
}
|
|
|
|
int isupper(int c)
|
|
{
|
|
int res;
|
|
InitCTypeLocale();
|
|
res = IsUpper(ctypeLocale, (ULONG)c);
|
|
CleanupCTypeLocale();
|
|
return res;
|
|
}
|
|
|
|
int iscntrl(int c)
|
|
{
|
|
int res;
|
|
InitCTypeLocale();
|
|
res = IsCntrl(ctypeLocale, (ULONG)c);
|
|
CleanupCTypeLocale();
|
|
return res;
|
|
}
|
|
/**********************************************************************/
|
|
#endif
|
|
|
|
struct Device *TimerBase = NULL;
|
|
struct timerequest *request = NULL;
|
|
|
|
int delete_timer()
|
|
{
|
|
struct MsgPort *port;
|
|
if (request == NULL)
|
|
return 1;
|
|
|
|
port = request->tr_node.io_Message.mn_ReplyPort;
|
|
|
|
if (port != 0)
|
|
DeletePort(port);
|
|
|
|
CloseDevice((struct IORequest*)request);
|
|
DeleteExtIO((struct IORequest*)request);
|
|
|
|
return 0;
|
|
}
|
|
|
|
int create_timer()
|
|
{
|
|
LONG error;
|
|
struct MsgPort *port = CreatePort(0, 0);
|
|
if (port == NULL)
|
|
return 1;
|
|
|
|
request = (struct timerequest*)CreateExtIO(port, sizeof(struct timerequest));
|
|
if (request == NULL)
|
|
{
|
|
DeletePort(port);
|
|
return 1;
|
|
}
|
|
|
|
error = OpenDevice(TIMERNAME, UNIT_MICROHZ, (struct IORequest*)request, 0L);
|
|
if (error != 0)
|
|
{
|
|
delete_timer(request);
|
|
return 1;
|
|
}
|
|
|
|
TimerBase = (struct Device*)request->tr_node.io_Device;
|
|
|
|
return 0;
|
|
}
|
|
|
|
/**
|
|
*
|
|
* @brief
|
|
* The time () function returns the value of time in seconds since 0 hours,
|
|
* 0 minutes, 0 seconds, January 1, 1970, Coordinated Universal Time. If an
|
|
* error occurs, time () returns 0.
|
|
*
|
|
* The return value is also stored in * tloc , provided that tloc is non-null.
|
|
*
|
|
*/
|
|
time_t time(time_t *tloc)
|
|
{
|
|
struct timeval tv;
|
|
time_t time;
|
|
int error;
|
|
|
|
error = create_timer();
|
|
if (error != 0) {
|
|
return 0;
|
|
}
|
|
|
|
GetSysTime(&tv);
|
|
time = (time_t)(tv.tv_sec + AMIGAOFFSET);
|
|
time = time - get_gmtoffset(time);
|
|
|
|
if (tloc) {
|
|
*tloc = time;
|
|
}
|
|
|
|
delete_timer();
|
|
|
|
return time;
|
|
}
|
|
|
|
int get_gmtoffset(time_t locale_time)
|
|
{
|
|
struct Library* localeBase;
|
|
struct Locale* locale;
|
|
struct tm tm;
|
|
timezone_t tz;
|
|
char *tzvar;
|
|
int gmtoffset = 0;
|
|
|
|
tzvar = AllocVec(ENVSIZE, MEMF_ANY | MEMF_CLEAR);
|
|
GetVar(TZVARIABLE, tzvar, ENVSIZE - 1, GVF_GLOBAL_ONLY);
|
|
tz = tzalloc(tzvar);
|
|
|
|
if (tz) {
|
|
// Localtime defined by TZ
|
|
localtime_rz(tz, &locale_time, &tm);
|
|
tzfree(tz);
|
|
gmtoffset = tm.tm_gmtoff;
|
|
} else {
|
|
// Localtime defined by AmigaOS
|
|
localeBase = OpenLibrary(LOCALELIB_NAME, LOCALELIB_REV);
|
|
if (localeBase == NULL) {
|
|
return 0;
|
|
}
|
|
|
|
locale = OpenLocale(NULL);
|
|
if (locale == NULL) {
|
|
CloseLibrary(localeBase);
|
|
return 0;
|
|
}
|
|
|
|
gmtoffset = locale->loc_GMTOffset * 60 * 60;
|
|
|
|
CloseLocale(locale);
|
|
CloseLibrary((struct Library*)localeBase);
|
|
}
|
|
|
|
FreeVec(tzvar);
|
|
return gmtoffset;
|
|
}
|
|
|
|
int get_gmtoffset_now()
|
|
{
|
|
struct tm *tm;
|
|
time_t now = time(NULL);
|
|
tm = localtime(&now);
|
|
return tm->tm_gmtoff;
|
|
}
|
|
|
|
/**********************************************************************/
|
|
int settimeofday(const struct timeval *tv, const struct timezone *tz)
|
|
{
|
|
int error;
|
|
|
|
error = create_timer();
|
|
if (error != 0) {
|
|
return error;
|
|
}
|
|
|
|
request->tr_node.io_Command = TR_SETSYSTIME;
|
|
request->tr_time.tv_secs = (long)tv->tv_secs - AMIGAOFFSET;
|
|
request->tr_time.tv_micro = tv->tv_micro;
|
|
DoIO((struct IORequest*)request);
|
|
|
|
error = delete_timer();
|
|
|
|
return error;
|
|
}
|
|
/**********************************************************************/
|
|
int gettime(struct timeval *tv)
|
|
{
|
|
int error = create_timer();
|
|
if (error != 0) {
|
|
return error;
|
|
}
|
|
|
|
GetSysTime(tv);
|
|
|
|
error = delete_timer();
|
|
|
|
return error;
|
|
}
|
|
|
|
int settime(struct timeval *tv)
|
|
{
|
|
int error = create_timer();
|
|
if (error != 0) {
|
|
return error;
|
|
}
|
|
|
|
request->tr_node.io_Command = TR_SETSYSTIME;
|
|
request->tr_time.tv_secs = (long)tv->tv_secs;
|
|
request->tr_time.tv_micro = tv->tv_micro;
|
|
DoIO((struct IORequest*)request);
|
|
|
|
error = delete_timer();
|
|
|
|
return error;
|
|
}
|
|
/**********************************************************************/
|
|
void underscore_add(char *string)
|
|
{
|
|
char *s = string;
|
|
while (*s) {
|
|
if (*s == ' ') {
|
|
*s = '_';
|
|
}
|
|
s++;
|
|
}
|
|
}
|
|
|
|
void underscore_remove(char *string)
|
|
{
|
|
char *s = string;
|
|
while (*s) {
|
|
if (*s == '_') {
|
|
*s = ' ';
|
|
}
|
|
s++;
|
|
}
|
|
}
|
|
/**********************************************************************/
|
|
void CopyFile(BPTR from, BPTR to)
|
|
{
|
|
const int bufsize = 512;
|
|
STRPTR buffer;
|
|
LONG s;
|
|
|
|
buffer = (STRPTR)AllocMem(bufsize, MEMF_PUBLIC);
|
|
|
|
if (!buffer) {
|
|
return;
|
|
}
|
|
|
|
do {
|
|
Flush(from);
|
|
if ((s = Read(from, buffer, bufsize)) == -1 || Write(to, buffer, s) != s)
|
|
{
|
|
break;
|
|
}
|
|
} while (s > 0);
|
|
|
|
FreeMem(buffer, bufsize);
|
|
}
|
|
/**********************************************************************/
|
|
void copyfile(char *fromname, char *toname)
|
|
{
|
|
BPTR fromfile, tofile;
|
|
|
|
fromfile = Open(fromname, MODE_OLDFILE);
|
|
if (!fromfile) {
|
|
fprintf(stderr, "Can't read %s\n", fromname);
|
|
exit(EXIT_FAILURE);
|
|
}
|
|
|
|
tofile = Open(toname, MODE_NEWFILE);
|
|
if (!tofile) {
|
|
Close(fromfile);
|
|
fprintf(stderr, "Can't create %s\n", toname);
|
|
exit(EXIT_FAILURE);
|
|
}
|
|
|
|
CopyFile(fromfile, tofile);
|
|
|
|
Close(tofile);
|
|
Close(fromfile);
|
|
}
|
|
/**********************************************************************/
|
|
|