mirror of
https://github.com/postgres/postgres.git
synced 2025-11-10 17:42:29 +03:00
Massive commit to run PGINDENT on all *.c and *.h files.
This commit is contained in:
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -1,13 +1,13 @@
|
||||
/*-------------------------------------------------------------------------
|
||||
*
|
||||
* dbcommands.c--
|
||||
*
|
||||
*
|
||||
*
|
||||
* Copyright (c) 1994, Regents of the University of California
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/parser/Attic/dbcommands.c,v 1.6 1997/08/19 21:32:14 momjian Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/parser/Attic/dbcommands.c,v 1.7 1997/09/07 04:44:45 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@@ -16,7 +16,7 @@
|
||||
#include <signal.h>
|
||||
|
||||
#include "postgres.h"
|
||||
#include "miscadmin.h" /* for DataDir */
|
||||
#include "miscadmin.h" /* for DataDir */
|
||||
#include "access/heapam.h"
|
||||
#include "access/htup.h"
|
||||
#include "access/relscan.h"
|
||||
@@ -35,228 +35,253 @@
|
||||
|
||||
|
||||
/* non-export function prototypes */
|
||||
static void check_permissions(char *command, char *dbname,
|
||||
Oid *dbIdP, Oid *userIdP);
|
||||
static void
|
||||
check_permissions(char *command, char *dbname,
|
||||
Oid * dbIdP, Oid * userIdP);
|
||||
static HeapTuple get_pg_dbtup(char *command, char *dbname, Relation dbrel);
|
||||
static void stop_vacuum(char *dbname);
|
||||
static void stop_vacuum(char *dbname);
|
||||
|
||||
void
|
||||
createdb(char *dbname)
|
||||
{
|
||||
Oid db_id, user_id;
|
||||
char buf[512];
|
||||
|
||||
/*
|
||||
* If this call returns, the database does not exist and we're allowed
|
||||
* to create databases.
|
||||
*/
|
||||
check_permissions("createdb", dbname, &db_id, &user_id);
|
||||
|
||||
/* close virtual file descriptors so we can do system() calls */
|
||||
closeAllVfds();
|
||||
|
||||
sprintf(buf, "mkdir %s%cbase%c%s", DataDir, SEP_CHAR, SEP_CHAR, dbname);
|
||||
system(buf);
|
||||
sprintf(buf, "%s %s%cbase%ctemplate1%c* %s%cbase%c%s",
|
||||
COPY_CMD, DataDir, SEP_CHAR, SEP_CHAR, SEP_CHAR, DataDir,
|
||||
SEP_CHAR, SEP_CHAR, dbname);
|
||||
system(buf);
|
||||
Oid db_id,
|
||||
user_id;
|
||||
char buf[512];
|
||||
|
||||
/* sprintf(buf, "insert into pg_database (datname, datdba, datpath) \
|
||||
/*
|
||||
* If this call returns, the database does not exist and we're allowed
|
||||
* to create databases.
|
||||
*/
|
||||
check_permissions("createdb", dbname, &db_id, &user_id);
|
||||
|
||||
/* close virtual file descriptors so we can do system() calls */
|
||||
closeAllVfds();
|
||||
|
||||
sprintf(buf, "mkdir %s%cbase%c%s", DataDir, SEP_CHAR, SEP_CHAR, dbname);
|
||||
system(buf);
|
||||
sprintf(buf, "%s %s%cbase%ctemplate1%c* %s%cbase%c%s",
|
||||
COPY_CMD, DataDir, SEP_CHAR, SEP_CHAR, SEP_CHAR, DataDir,
|
||||
SEP_CHAR, SEP_CHAR, dbname);
|
||||
system(buf);
|
||||
|
||||
/* sprintf(buf, "insert into pg_database (datname, datdba, datpath) \
|
||||
values (\'%s\'::char16, \'%d\'::oid, \'%s\'::text);",
|
||||
dbname, user_id, dbname);
|
||||
dbname, user_id, dbname);
|
||||
*/
|
||||
sprintf(buf, "insert into pg_database (datname, datdba, datpath) \
|
||||
sprintf(buf, "insert into pg_database (datname, datdba, datpath) \
|
||||
values (\'%s\', \'%d\', \'%s\');",
|
||||
dbname, user_id, dbname);
|
||||
dbname, user_id, dbname);
|
||||
|
||||
pg_eval(buf, (char **) NULL, (Oid *) NULL, 0);
|
||||
pg_eval(buf, (char **) NULL, (Oid *) NULL, 0);
|
||||
}
|
||||
|
||||
void
|
||||
destroydb(char *dbname)
|
||||
{
|
||||
Oid user_id, db_id;
|
||||
char buf[512];
|
||||
|
||||
/*
|
||||
* If this call returns, the database exists and we're allowed to
|
||||
* remove it.
|
||||
*/
|
||||
check_permissions("destroydb", dbname, &db_id, &user_id);
|
||||
|
||||
if (!OidIsValid(db_id)) {
|
||||
elog(FATAL, "impossible: pg_database instance with invalid OID.");
|
||||
}
|
||||
|
||||
/* stop the vacuum daemon */
|
||||
stop_vacuum(dbname);
|
||||
|
||||
/* remove the pg_database tuple FIRST,
|
||||
this may fail due to permissions problems*/
|
||||
sprintf(buf, "delete from pg_database where pg_database.oid = \'%d\'::oid",
|
||||
db_id);
|
||||
pg_eval(buf, (char **) NULL, (Oid *) NULL, 0);
|
||||
|
||||
/* remove the data directory. If the DELETE above failed, this will
|
||||
not be reached */
|
||||
sprintf(buf, "rm -r %s/base/%s", DataDir, dbname);
|
||||
system(buf);
|
||||
|
||||
/* drop pages for this database that are in the shared buffer cache */
|
||||
DropBuffers(db_id);
|
||||
Oid user_id,
|
||||
db_id;
|
||||
char buf[512];
|
||||
|
||||
/*
|
||||
* If this call returns, the database exists and we're allowed to
|
||||
* remove it.
|
||||
*/
|
||||
check_permissions("destroydb", dbname, &db_id, &user_id);
|
||||
|
||||
if (!OidIsValid(db_id))
|
||||
{
|
||||
elog(FATAL, "impossible: pg_database instance with invalid OID.");
|
||||
}
|
||||
|
||||
/* stop the vacuum daemon */
|
||||
stop_vacuum(dbname);
|
||||
|
||||
/*
|
||||
* remove the pg_database tuple FIRST, this may fail due to
|
||||
* permissions problems
|
||||
*/
|
||||
sprintf(buf, "delete from pg_database where pg_database.oid = \'%d\'::oid",
|
||||
db_id);
|
||||
pg_eval(buf, (char **) NULL, (Oid *) NULL, 0);
|
||||
|
||||
/*
|
||||
* remove the data directory. If the DELETE above failed, this will
|
||||
* not be reached
|
||||
*/
|
||||
sprintf(buf, "rm -r %s/base/%s", DataDir, dbname);
|
||||
system(buf);
|
||||
|
||||
/* drop pages for this database that are in the shared buffer cache */
|
||||
DropBuffers(db_id);
|
||||
}
|
||||
|
||||
static HeapTuple
|
||||
static HeapTuple
|
||||
get_pg_dbtup(char *command, char *dbname, Relation dbrel)
|
||||
{
|
||||
HeapTuple dbtup;
|
||||
HeapTuple tup;
|
||||
Buffer buf;
|
||||
HeapScanDesc scan;
|
||||
ScanKeyData scanKey;
|
||||
|
||||
ScanKeyEntryInitialize(&scanKey, 0, Anum_pg_database_datname,
|
||||
NameEqualRegProcedure, NameGetDatum(dbname));
|
||||
|
||||
scan = heap_beginscan(dbrel, 0, NowTimeQual, 1, &scanKey);
|
||||
if (!HeapScanIsValid(scan))
|
||||
elog(WARN, "%s: cannot begin scan of pg_database.", command);
|
||||
|
||||
/*
|
||||
* since we want to return the tuple out of this proc, and we're
|
||||
* going to close the relation, copy the tuple and return the copy.
|
||||
*/
|
||||
tup = heap_getnext(scan, 0, &buf);
|
||||
|
||||
if (HeapTupleIsValid(tup)) {
|
||||
dbtup = heap_copytuple(tup);
|
||||
ReleaseBuffer(buf);
|
||||
} else
|
||||
dbtup = tup;
|
||||
|
||||
heap_endscan(scan);
|
||||
return (dbtup);
|
||||
HeapTuple dbtup;
|
||||
HeapTuple tup;
|
||||
Buffer buf;
|
||||
HeapScanDesc scan;
|
||||
ScanKeyData scanKey;
|
||||
|
||||
ScanKeyEntryInitialize(&scanKey, 0, Anum_pg_database_datname,
|
||||
NameEqualRegProcedure, NameGetDatum(dbname));
|
||||
|
||||
scan = heap_beginscan(dbrel, 0, NowTimeQual, 1, &scanKey);
|
||||
if (!HeapScanIsValid(scan))
|
||||
elog(WARN, "%s: cannot begin scan of pg_database.", command);
|
||||
|
||||
/*
|
||||
* since we want to return the tuple out of this proc, and we're going
|
||||
* to close the relation, copy the tuple and return the copy.
|
||||
*/
|
||||
tup = heap_getnext(scan, 0, &buf);
|
||||
|
||||
if (HeapTupleIsValid(tup))
|
||||
{
|
||||
dbtup = heap_copytuple(tup);
|
||||
ReleaseBuffer(buf);
|
||||
}
|
||||
else
|
||||
dbtup = tup;
|
||||
|
||||
heap_endscan(scan);
|
||||
return (dbtup);
|
||||
}
|
||||
|
||||
/*
|
||||
* check_permissions() -- verify that the user is permitted to do this.
|
||||
* check_permissions() -- verify that the user is permitted to do this.
|
||||
*
|
||||
* If the user is not allowed to carry out this operation, this routine
|
||||
* elog(WARN, ...)s, which will abort the xact. As a side effect, the
|
||||
* user's pg_user tuple OID is returned in userIdP and the target database's
|
||||
* OID is returned in dbIdP.
|
||||
* If the user is not allowed to carry out this operation, this routine
|
||||
* elog(WARN, ...)s, which will abort the xact. As a side effect, the
|
||||
* user's pg_user tuple OID is returned in userIdP and the target database's
|
||||
* OID is returned in dbIdP.
|
||||
*/
|
||||
|
||||
static void
|
||||
check_permissions(char *command,
|
||||
char *dbname,
|
||||
Oid *dbIdP,
|
||||
Oid *userIdP)
|
||||
char *dbname,
|
||||
Oid * dbIdP,
|
||||
Oid * userIdP)
|
||||
{
|
||||
Relation dbrel;
|
||||
HeapTuple dbtup, utup;
|
||||
Oid dbowner = (Oid)0;
|
||||
char use_createdb;
|
||||
bool dbfound;
|
||||
bool use_super;
|
||||
char *userName;
|
||||
Relation dbrel;
|
||||
HeapTuple dbtup,
|
||||
utup;
|
||||
Oid dbowner = (Oid) 0;
|
||||
char use_createdb;
|
||||
bool dbfound;
|
||||
bool use_super;
|
||||
char *userName;
|
||||
|
||||
userName = GetPgUserName();
|
||||
utup = SearchSysCacheTuple(USENAME, PointerGetDatum(userName),
|
||||
0,0,0);
|
||||
*userIdP = ((Form_pg_user)GETSTRUCT(utup))->usesysid;
|
||||
use_super = ((Form_pg_user)GETSTRUCT(utup))->usesuper;
|
||||
use_createdb = ((Form_pg_user)GETSTRUCT(utup))->usecreatedb;
|
||||
|
||||
/* Check to make sure user has permission to use createdb */
|
||||
if (!use_createdb) {
|
||||
elog(WARN, "user \"%s\" is not allowed to create/destroy databases",
|
||||
userName);
|
||||
}
|
||||
|
||||
/* Make sure we are not mucking with the template database */
|
||||
if (!strcmp(dbname, "template1")) {
|
||||
elog(WARN, "%s cannot be executed on the template database.", command);
|
||||
}
|
||||
|
||||
/* Check to make sure database is not the currently open database */
|
||||
if (!strcmp(dbname, GetDatabaseName())) {
|
||||
elog(WARN, "%s cannot be executed on an open database", command);
|
||||
}
|
||||
|
||||
/* Check to make sure database is owned by this user */
|
||||
|
||||
/*
|
||||
* need the reldesc to get the database owner out of dbtup
|
||||
* and to set a write lock on it.
|
||||
*/
|
||||
dbrel = heap_openr(DatabaseRelationName);
|
||||
|
||||
if (!RelationIsValid(dbrel))
|
||||
elog(FATAL, "%s: cannot open relation \"%-.*s\"",
|
||||
command, DatabaseRelationName);
|
||||
|
||||
/*
|
||||
* Acquire a write lock on pg_database from the beginning to avoid
|
||||
* upgrading a read lock to a write lock. Upgrading causes long delays
|
||||
* when multiple 'createdb's or 'destroydb's are run simult. -mer 7/3/91
|
||||
*/
|
||||
RelationSetLockForWrite(dbrel);
|
||||
dbtup = get_pg_dbtup(command, dbname, dbrel);
|
||||
dbfound = HeapTupleIsValid(dbtup);
|
||||
|
||||
if (dbfound) {
|
||||
dbowner = (Oid) heap_getattr(dbtup, InvalidBuffer,
|
||||
Anum_pg_database_datdba,
|
||||
RelationGetTupleDescriptor(dbrel),
|
||||
(char *) NULL);
|
||||
*dbIdP = dbtup->t_oid;
|
||||
} else {
|
||||
*dbIdP = InvalidOid;
|
||||
}
|
||||
|
||||
heap_close(dbrel);
|
||||
|
||||
/*
|
||||
* Now be sure that the user is allowed to do this.
|
||||
*/
|
||||
|
||||
if (dbfound && !strcmp(command, "createdb")) {
|
||||
|
||||
elog(WARN, "createdb: database %s already exists.", dbname);
|
||||
|
||||
} else if (!dbfound && !strcmp(command, "destroydb")) {
|
||||
|
||||
elog(WARN, "destroydb: database %s does not exist.", dbname);
|
||||
|
||||
} else if (dbfound && !strcmp(command, "destroydb")
|
||||
&& dbowner != *userIdP && use_super == false) {
|
||||
|
||||
elog(WARN, "%s: database %s is not owned by you.", command, dbname);
|
||||
|
||||
}
|
||||
userName = GetPgUserName();
|
||||
utup = SearchSysCacheTuple(USENAME, PointerGetDatum(userName),
|
||||
0, 0, 0);
|
||||
*userIdP = ((Form_pg_user) GETSTRUCT(utup))->usesysid;
|
||||
use_super = ((Form_pg_user) GETSTRUCT(utup))->usesuper;
|
||||
use_createdb = ((Form_pg_user) GETSTRUCT(utup))->usecreatedb;
|
||||
|
||||
/* Check to make sure user has permission to use createdb */
|
||||
if (!use_createdb)
|
||||
{
|
||||
elog(WARN, "user \"%s\" is not allowed to create/destroy databases",
|
||||
userName);
|
||||
}
|
||||
|
||||
/* Make sure we are not mucking with the template database */
|
||||
if (!strcmp(dbname, "template1"))
|
||||
{
|
||||
elog(WARN, "%s cannot be executed on the template database.", command);
|
||||
}
|
||||
|
||||
/* Check to make sure database is not the currently open database */
|
||||
if (!strcmp(dbname, GetDatabaseName()))
|
||||
{
|
||||
elog(WARN, "%s cannot be executed on an open database", command);
|
||||
}
|
||||
|
||||
/* Check to make sure database is owned by this user */
|
||||
|
||||
/*
|
||||
* need the reldesc to get the database owner out of dbtup and to set
|
||||
* a write lock on it.
|
||||
*/
|
||||
dbrel = heap_openr(DatabaseRelationName);
|
||||
|
||||
if (!RelationIsValid(dbrel))
|
||||
elog(FATAL, "%s: cannot open relation \"%-.*s\"",
|
||||
command, DatabaseRelationName);
|
||||
|
||||
/*
|
||||
* Acquire a write lock on pg_database from the beginning to avoid
|
||||
* upgrading a read lock to a write lock. Upgrading causes long
|
||||
* delays when multiple 'createdb's or 'destroydb's are run simult.
|
||||
* -mer 7/3/91
|
||||
*/
|
||||
RelationSetLockForWrite(dbrel);
|
||||
dbtup = get_pg_dbtup(command, dbname, dbrel);
|
||||
dbfound = HeapTupleIsValid(dbtup);
|
||||
|
||||
if (dbfound)
|
||||
{
|
||||
dbowner = (Oid) heap_getattr(dbtup, InvalidBuffer,
|
||||
Anum_pg_database_datdba,
|
||||
RelationGetTupleDescriptor(dbrel),
|
||||
(char *) NULL);
|
||||
*dbIdP = dbtup->t_oid;
|
||||
}
|
||||
else
|
||||
{
|
||||
*dbIdP = InvalidOid;
|
||||
}
|
||||
|
||||
heap_close(dbrel);
|
||||
|
||||
/*
|
||||
* Now be sure that the user is allowed to do this.
|
||||
*/
|
||||
|
||||
if (dbfound && !strcmp(command, "createdb"))
|
||||
{
|
||||
|
||||
elog(WARN, "createdb: database %s already exists.", dbname);
|
||||
|
||||
}
|
||||
else if (!dbfound && !strcmp(command, "destroydb"))
|
||||
{
|
||||
|
||||
elog(WARN, "destroydb: database %s does not exist.", dbname);
|
||||
|
||||
}
|
||||
else if (dbfound && !strcmp(command, "destroydb")
|
||||
&& dbowner != *userIdP && use_super == false)
|
||||
{
|
||||
|
||||
elog(WARN, "%s: database %s is not owned by you.", command, dbname);
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* stop_vacuum() -- stop the vacuum daemon on the database, if one is
|
||||
* running.
|
||||
* stop_vacuum() -- stop the vacuum daemon on the database, if one is
|
||||
* running.
|
||||
*/
|
||||
static void
|
||||
stop_vacuum(char *dbname)
|
||||
{
|
||||
char filename[256];
|
||||
FILE *fp;
|
||||
int pid;
|
||||
|
||||
sprintf(filename, "%s%cbase%c%s%c%s.vacuum", DataDir, SEP_CHAR, SEP_CHAR,
|
||||
dbname, SEP_CHAR, dbname);
|
||||
if ((fp = AllocateFile(filename, "r")) != NULL) {
|
||||
fscanf(fp, "%d", &pid);
|
||||
FreeFile(fp);
|
||||
if (kill(pid, SIGKILLDAEMON1) < 0) {
|
||||
elog(WARN, "can't kill vacuum daemon (pid %d) on %s",
|
||||
pid, dbname);
|
||||
char filename[256];
|
||||
FILE *fp;
|
||||
int pid;
|
||||
|
||||
sprintf(filename, "%s%cbase%c%s%c%s.vacuum", DataDir, SEP_CHAR, SEP_CHAR,
|
||||
dbname, SEP_CHAR, dbname);
|
||||
if ((fp = AllocateFile(filename, "r")) != NULL)
|
||||
{
|
||||
fscanf(fp, "%d", &pid);
|
||||
FreeFile(fp);
|
||||
if (kill(pid, SIGKILLDAEMON1) < 0)
|
||||
{
|
||||
elog(WARN, "can't kill vacuum daemon (pid %d) on %s",
|
||||
pid, dbname);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
/*-------------------------------------------------------------------------
|
||||
*
|
||||
* keywords.c--
|
||||
* lexical token lookup for reserved words in postgres SQL
|
||||
* lexical token lookup for reserved words in postgres SQL
|
||||
*
|
||||
* Copyright (c) 1994, Regents of the University of California
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/parser/keywords.c,v 1.14 1997/09/04 13:24:26 vadim Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/parser/keywords.c,v 1.15 1997/09/07 04:44:47 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@@ -20,202 +20,204 @@
|
||||
#include "parse.h"
|
||||
#include "utils/elog.h"
|
||||
#include "parser/keywords.h"
|
||||
#include "parser/dbcommands.h" /* createdb, destroydb stop_vacuum */
|
||||
#include "parser/dbcommands.h" /* createdb, destroydb stop_vacuum */
|
||||
|
||||
|
||||
/*
|
||||
* List of (keyword-name, keyword-token-value) pairs.
|
||||
*
|
||||
* !!WARNING!!: This list must be sorted, because binary
|
||||
* search is used to locate entries.
|
||||
* search is used to locate entries.
|
||||
*/
|
||||
static ScanKeyword ScanKeywords[] = {
|
||||
/* name value */
|
||||
{ "abort", ABORT_TRANS },
|
||||
{ "acl", ACL },
|
||||
{ "add", ADD },
|
||||
{ "after", AFTER },
|
||||
{ "aggregate", AGGREGATE },
|
||||
{ "all", ALL },
|
||||
{ "alter", ALTER },
|
||||
{ "analyze", ANALYZE },
|
||||
{ "and", AND },
|
||||
{ "append", APPEND },
|
||||
{ "archIve", ARCHIVE }, /* XXX crooked: I < _ */
|
||||
{ "arch_store", ARCH_STORE },
|
||||
{ "archive", ARCHIVE }, /* XXX crooked: i > _ */
|
||||
{ "as", AS },
|
||||
{ "asc", ASC },
|
||||
{ "backward", BACKWARD },
|
||||
{ "before", BEFORE },
|
||||
{ "begin", BEGIN_TRANS },
|
||||
{ "between", BETWEEN },
|
||||
{ "binary", BINARY },
|
||||
{ "both", BOTH },
|
||||
{ "by", BY },
|
||||
{ "cast", CAST },
|
||||
{ "change", CHANGE },
|
||||
{ "check", CHECK },
|
||||
{ "close", CLOSE },
|
||||
{ "cluster", CLUSTER },
|
||||
{ "column", COLUMN },
|
||||
{ "commit", COMMIT },
|
||||
{ "constraint", CONSTRAINT },
|
||||
{ "copy", COPY },
|
||||
{ "create", CREATE },
|
||||
{ "cross", CROSS },
|
||||
{ "current", CURRENT },
|
||||
{ "cursor", CURSOR },
|
||||
{ "database", DATABASE },
|
||||
{ "day", DAYINTERVAL },
|
||||
{ "declare", DECLARE },
|
||||
{ "default", DEFAULT },
|
||||
{ "delete", DELETE },
|
||||
{ "delimiters", DELIMITERS },
|
||||
{ "desc", DESC },
|
||||
{ "distinct", DISTINCT },
|
||||
{ "do", DO },
|
||||
{ "drop", DROP },
|
||||
{ "end", END_TRANS },
|
||||
{ "execute", EXECUTE },
|
||||
{ "exists", EXISTS },
|
||||
{ "explain", EXPLAIN },
|
||||
{ "extend", EXTEND },
|
||||
{ "extract", EXTRACT },
|
||||
{ "fetch", FETCH },
|
||||
{ "for", FOR },
|
||||
{ "forward", FORWARD },
|
||||
{ "from", FROM },
|
||||
{ "full", FULL },
|
||||
{ "function", FUNCTION },
|
||||
{ "grant", GRANT },
|
||||
{ "group", GROUP },
|
||||
{ "having", HAVING },
|
||||
{ "heavy", HEAVY },
|
||||
{ "hour", HOURINTERVAL },
|
||||
{ "in", IN },
|
||||
{ "index", INDEX },
|
||||
{ "inherits", INHERITS },
|
||||
{ "inner", INNERJOIN },
|
||||
{ "insert", INSERT },
|
||||
{ "instead", INSTEAD },
|
||||
{ "interval", INTERVAL },
|
||||
{ "into", INTO },
|
||||
{ "is", IS },
|
||||
{ "isnull", ISNULL },
|
||||
{ "join", JOIN },
|
||||
{ "language", LANGUAGE },
|
||||
{ "leading", LEADING },
|
||||
{ "left", LEFT },
|
||||
{ "light", LIGHT },
|
||||
{ "like", LIKE },
|
||||
{ "listen", LISTEN },
|
||||
{ "load", LOAD },
|
||||
{ "local", LOCAL },
|
||||
{ "merge", MERGE },
|
||||
{ "minute", MINUTEINTERVAL },
|
||||
{ "month", MONTHINTERVAL },
|
||||
{ "move", MOVE },
|
||||
{ "natural", NATURAL },
|
||||
{ "new", NEW },
|
||||
{ "none", NONE },
|
||||
{ "not", NOT },
|
||||
{ "nothing", NOTHING },
|
||||
{ "notify", NOTIFY },
|
||||
{ "notnull", NOTNULL },
|
||||
{ "null", PNULL },
|
||||
{ "oids", OIDS },
|
||||
{ "on", ON },
|
||||
{ "operator", OPERATOR },
|
||||
{ "option", OPTION },
|
||||
{ "or", OR },
|
||||
{ "order", ORDER },
|
||||
{ "outer", OUTERJOIN },
|
||||
{ "position", POSITION },
|
||||
{ "privileges", PRIVILEGES },
|
||||
{ "procedure", PROCEDURE },
|
||||
{ "public", PUBLIC },
|
||||
{ "purge", PURGE },
|
||||
{ "recipe", RECIPE },
|
||||
{ "rename", RENAME },
|
||||
{ "replace", REPLACE },
|
||||
{ "reset", RESET },
|
||||
{ "retrieve", RETRIEVE },
|
||||
{ "returns", RETURNS },
|
||||
{ "revoke", REVOKE },
|
||||
{ "right", RIGHT },
|
||||
{ "rollback", ROLLBACK },
|
||||
{ "rule", RULE },
|
||||
{ "second", SECONDINTERVAL },
|
||||
{ "select", SELECT },
|
||||
{ "sequence", SEQUENCE },
|
||||
{ "set", SET },
|
||||
{ "setof", SETOF },
|
||||
{ "show", SHOW },
|
||||
{ "stdin", STDIN },
|
||||
{ "stdout", STDOUT },
|
||||
{ "store", STORE },
|
||||
{ "substring", SUBSTRING },
|
||||
{ "table", TABLE },
|
||||
{ "time", TIME },
|
||||
{ "to", TO },
|
||||
{ "transaction", TRANSACTION },
|
||||
{ "trailing", TRAILING },
|
||||
{ "trigger", TRIGGER },
|
||||
{ "trim", TRIM },
|
||||
{ "type", P_TYPE },
|
||||
{ "union", UNION },
|
||||
{ "unique", UNIQUE },
|
||||
{ "update", UPDATE },
|
||||
{ "using", USING },
|
||||
{ "vacuum", VACUUM },
|
||||
{ "values", VALUES },
|
||||
{ "verbose", VERBOSE },
|
||||
{ "version", VERSION },
|
||||
{ "view", VIEW },
|
||||
{ "where", WHERE },
|
||||
{ "with", WITH },
|
||||
{ "work", WORK },
|
||||
{ "year", YEARINTERVAL },
|
||||
{ "zone", ZONE },
|
||||
/* name value */
|
||||
{"abort", ABORT_TRANS},
|
||||
{"acl", ACL},
|
||||
{"add", ADD},
|
||||
{"after", AFTER},
|
||||
{"aggregate", AGGREGATE},
|
||||
{"all", ALL},
|
||||
{"alter", ALTER},
|
||||
{"analyze", ANALYZE},
|
||||
{"and", AND},
|
||||
{"append", APPEND},
|
||||
{"archIve", ARCHIVE}, /* XXX crooked: I < _ */
|
||||
{"arch_store", ARCH_STORE},
|
||||
{"archive", ARCHIVE}, /* XXX crooked: i > _ */
|
||||
{"as", AS},
|
||||
{"asc", ASC},
|
||||
{"backward", BACKWARD},
|
||||
{"before", BEFORE},
|
||||
{"begin", BEGIN_TRANS},
|
||||
{"between", BETWEEN},
|
||||
{"binary", BINARY},
|
||||
{"both", BOTH},
|
||||
{"by", BY},
|
||||
{"cast", CAST},
|
||||
{"change", CHANGE},
|
||||
{"check", CHECK},
|
||||
{"close", CLOSE},
|
||||
{"cluster", CLUSTER},
|
||||
{"column", COLUMN},
|
||||
{"commit", COMMIT},
|
||||
{"constraint", CONSTRAINT},
|
||||
{"copy", COPY},
|
||||
{"create", CREATE},
|
||||
{"cross", CROSS},
|
||||
{"current", CURRENT},
|
||||
{"cursor", CURSOR},
|
||||
{"database", DATABASE},
|
||||
{"day", DAYINTERVAL},
|
||||
{"declare", DECLARE},
|
||||
{"default", DEFAULT},
|
||||
{"delete", DELETE},
|
||||
{"delimiters", DELIMITERS},
|
||||
{"desc", DESC},
|
||||
{"distinct", DISTINCT},
|
||||
{"do", DO},
|
||||
{"drop", DROP},
|
||||
{"end", END_TRANS},
|
||||
{"execute", EXECUTE},
|
||||
{"exists", EXISTS},
|
||||
{"explain", EXPLAIN},
|
||||
{"extend", EXTEND},
|
||||
{"extract", EXTRACT},
|
||||
{"fetch", FETCH},
|
||||
{"for", FOR},
|
||||
{"forward", FORWARD},
|
||||
{"from", FROM},
|
||||
{"full", FULL},
|
||||
{"function", FUNCTION},
|
||||
{"grant", GRANT},
|
||||
{"group", GROUP},
|
||||
{"having", HAVING},
|
||||
{"heavy", HEAVY},
|
||||
{"hour", HOURINTERVAL},
|
||||
{"in", IN},
|
||||
{"index", INDEX},
|
||||
{"inherits", INHERITS},
|
||||
{"inner", INNERJOIN},
|
||||
{"insert", INSERT},
|
||||
{"instead", INSTEAD},
|
||||
{"interval", INTERVAL},
|
||||
{"into", INTO},
|
||||
{"is", IS},
|
||||
{"isnull", ISNULL},
|
||||
{"join", JOIN},
|
||||
{"language", LANGUAGE},
|
||||
{"leading", LEADING},
|
||||
{"left", LEFT},
|
||||
{"light", LIGHT},
|
||||
{"like", LIKE},
|
||||
{"listen", LISTEN},
|
||||
{"load", LOAD},
|
||||
{"local", LOCAL},
|
||||
{"merge", MERGE},
|
||||
{"minute", MINUTEINTERVAL},
|
||||
{"month", MONTHINTERVAL},
|
||||
{"move", MOVE},
|
||||
{"natural", NATURAL},
|
||||
{"new", NEW},
|
||||
{"none", NONE},
|
||||
{"not", NOT},
|
||||
{"nothing", NOTHING},
|
||||
{"notify", NOTIFY},
|
||||
{"notnull", NOTNULL},
|
||||
{"null", PNULL},
|
||||
{"oids", OIDS},
|
||||
{"on", ON},
|
||||
{"operator", OPERATOR},
|
||||
{"option", OPTION},
|
||||
{"or", OR},
|
||||
{"order", ORDER},
|
||||
{"outer", OUTERJOIN},
|
||||
{"position", POSITION},
|
||||
{"privileges", PRIVILEGES},
|
||||
{"procedure", PROCEDURE},
|
||||
{"public", PUBLIC},
|
||||
{"purge", PURGE},
|
||||
{"recipe", RECIPE},
|
||||
{"rename", RENAME},
|
||||
{"replace", REPLACE},
|
||||
{"reset", RESET},
|
||||
{"retrieve", RETRIEVE},
|
||||
{"returns", RETURNS},
|
||||
{"revoke", REVOKE},
|
||||
{"right", RIGHT},
|
||||
{"rollback", ROLLBACK},
|
||||
{"rule", RULE},
|
||||
{"second", SECONDINTERVAL},
|
||||
{"select", SELECT},
|
||||
{"sequence", SEQUENCE},
|
||||
{"set", SET},
|
||||
{"setof", SETOF},
|
||||
{"show", SHOW},
|
||||
{"stdin", STDIN},
|
||||
{"stdout", STDOUT},
|
||||
{"store", STORE},
|
||||
{"substring", SUBSTRING},
|
||||
{"table", TABLE},
|
||||
{"time", TIME},
|
||||
{"to", TO},
|
||||
{"transaction", TRANSACTION},
|
||||
{"trailing", TRAILING},
|
||||
{"trigger", TRIGGER},
|
||||
{"trim", TRIM},
|
||||
{"type", P_TYPE},
|
||||
{"union", UNION},
|
||||
{"unique", UNIQUE},
|
||||
{"update", UPDATE},
|
||||
{"using", USING},
|
||||
{"vacuum", VACUUM},
|
||||
{"values", VALUES},
|
||||
{"verbose", VERBOSE},
|
||||
{"version", VERSION},
|
||||
{"view", VIEW},
|
||||
{"where", WHERE},
|
||||
{"with", WITH},
|
||||
{"work", WORK},
|
||||
{"year", YEARINTERVAL},
|
||||
{"zone", ZONE},
|
||||
};
|
||||
|
||||
ScanKeyword *
|
||||
ScanKeyword *
|
||||
ScanKeywordLookup(char *text)
|
||||
{
|
||||
ScanKeyword *low = &ScanKeywords[0];
|
||||
ScanKeyword *high = endof(ScanKeywords) - 1;
|
||||
ScanKeyword *middle;
|
||||
int difference;
|
||||
|
||||
while (low <= high) {
|
||||
middle = low + (high - low) / 2;
|
||||
difference = strcmp(middle->name, text);
|
||||
if (difference == 0)
|
||||
return (middle);
|
||||
else if (difference < 0)
|
||||
low = middle + 1;
|
||||
else
|
||||
high = middle - 1;
|
||||
}
|
||||
|
||||
return (NULL);
|
||||
ScanKeyword *low = &ScanKeywords[0];
|
||||
ScanKeyword *high = endof(ScanKeywords) - 1;
|
||||
ScanKeyword *middle;
|
||||
int difference;
|
||||
|
||||
while (low <= high)
|
||||
{
|
||||
middle = low + (high - low) / 2;
|
||||
difference = strcmp(middle->name, text);
|
||||
if (difference == 0)
|
||||
return (middle);
|
||||
else if (difference < 0)
|
||||
low = middle + 1;
|
||||
else
|
||||
high = middle - 1;
|
||||
}
|
||||
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
#ifdef NOT_USED
|
||||
char*
|
||||
char *
|
||||
AtomValueGetString(int atomval)
|
||||
{
|
||||
ScanKeyword *low = &ScanKeywords[0];
|
||||
ScanKeyword *high = endof(ScanKeywords) - 1;
|
||||
int keyword_list_length = (high-low);
|
||||
int i;
|
||||
|
||||
for (i=0; i < keyword_list_length ; i++ )
|
||||
if (ScanKeywords[i].value == atomval )
|
||||
return(ScanKeywords[i].name);
|
||||
|
||||
elog(WARN,"AtomGetString called with bogus atom # : %d", atomval );
|
||||
return(NULL);
|
||||
ScanKeyword *low = &ScanKeywords[0];
|
||||
ScanKeyword *high = endof(ScanKeywords) - 1;
|
||||
int keyword_list_length = (high - low);
|
||||
int i;
|
||||
|
||||
for (i = 0; i < keyword_list_length; i++)
|
||||
if (ScanKeywords[i].value == atomval)
|
||||
return (ScanKeywords[i].name);
|
||||
|
||||
elog(WARN, "AtomGetString called with bogus atom # : %d", atomval);
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -6,14 +6,14 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/parser/parser.c,v 1.22 1997/08/22 07:12:45 momjian Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/parser/parser.c,v 1.23 1997/09/07 04:44:50 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
#include <pwd.h>
|
||||
#include <sys/param.h> /* for MAXPATHLEN */
|
||||
#include <sys/param.h> /* for MAXPATHLEN */
|
||||
|
||||
#include "postgres.h"
|
||||
#include "parser/catalog_utils.h"
|
||||
@@ -34,456 +34,510 @@
|
||||
#include "catalog/pg_aggregate.h"
|
||||
#include "catalog/pg_type.h"
|
||||
#include "access/heapam.h"
|
||||
#include "optimizer/clauses.h"
|
||||
#include "optimizer/clauses.h"
|
||||
|
||||
void init_io(); /* from scan.l */
|
||||
void parser_init(Oid *typev, int nargs); /* from gram.y */
|
||||
int yyparse(); /* from gram.c */
|
||||
void init_io(); /* from scan.l */
|
||||
void parser_init(Oid * typev, int nargs); /* from gram.y */
|
||||
int yyparse(); /* from gram.c */
|
||||
|
||||
char *parseString; /* the char* which holds the string to be parsed */
|
||||
char *parseCh; /* a pointer used during parsing to walk down ParseString*/
|
||||
char *parseString; /* the char* which holds the string to be
|
||||
* parsed */
|
||||
char *parseCh; /* a pointer used during parsing to walk
|
||||
* down ParseString */
|
||||
|
||||
List *parsetree = NIL;
|
||||
List *parsetree = NIL;
|
||||
|
||||
#ifdef SETS_FIXED
|
||||
static void fixupsets();
|
||||
static void define_sets();
|
||||
static void fixupsets();
|
||||
static void define_sets();
|
||||
|
||||
#endif
|
||||
/*
|
||||
* parser-- returns a list of parse trees
|
||||
*
|
||||
* CALLER is responsible for free'ing the list returned
|
||||
*
|
||||
* CALLER is responsible for free'ing the list returned
|
||||
*/
|
||||
QueryTreeList *
|
||||
parser(char *str, Oid *typev, int nargs)
|
||||
QueryTreeList *
|
||||
parser(char *str, Oid * typev, int nargs)
|
||||
{
|
||||
QueryTreeList* queryList;
|
||||
int yyresult;
|
||||
QueryTreeList *queryList;
|
||||
int yyresult;
|
||||
|
||||
#if defined(FLEX_SCANNER)
|
||||
extern void DeleteBuffer(void);
|
||||
#endif /* FLEX_SCANNER */
|
||||
|
||||
init_io();
|
||||
|
||||
/* Set things up to read from the string, if there is one */
|
||||
parseString = (char *) palloc(strlen(str) + 1);
|
||||
memmove(parseString,str,strlen(str)+1);
|
||||
|
||||
parser_init(typev, nargs);
|
||||
yyresult = yyparse();
|
||||
extern void DeleteBuffer(void);
|
||||
|
||||
#endif /* FLEX_SCANNER */
|
||||
|
||||
init_io();
|
||||
|
||||
/* Set things up to read from the string, if there is one */
|
||||
parseString = (char *) palloc(strlen(str) + 1);
|
||||
memmove(parseString, str, strlen(str) + 1);
|
||||
|
||||
parser_init(typev, nargs);
|
||||
yyresult = yyparse();
|
||||
|
||||
#if defined(FLEX_SCANNER)
|
||||
DeleteBuffer();
|
||||
#endif /* FLEX_SCANNER */
|
||||
|
||||
clearerr(stdin);
|
||||
|
||||
if (yyresult) { /* error */
|
||||
return((QueryTreeList*)NULL);
|
||||
}
|
||||
DeleteBuffer();
|
||||
#endif /* FLEX_SCANNER */
|
||||
|
||||
clearerr(stdin);
|
||||
|
||||
if (yyresult)
|
||||
{ /* error */
|
||||
return ((QueryTreeList *) NULL);
|
||||
}
|
||||
|
||||
queryList = parse_analyze(parsetree);
|
||||
|
||||
queryList = parse_analyze(parsetree);
|
||||
|
||||
#ifdef SETS_FIXED
|
||||
/* Fixing up sets calls the parser, so it reassigns the global
|
||||
* variable parsetree. So save the real parsetree.
|
||||
*/
|
||||
savetree = parsetree;
|
||||
foreach (parse, savetree) { /* savetree is really a list of parses */
|
||||
|
||||
/* find set definitions embedded in query */
|
||||
fixupsets((Query *)lfirst(parse));
|
||||
/*
|
||||
* Fixing up sets calls the parser, so it reassigns the global
|
||||
* variable parsetree. So save the real parsetree.
|
||||
*/
|
||||
savetree = parsetree;
|
||||
foreach(parse, savetree)
|
||||
{ /* savetree is really a list of parses */
|
||||
|
||||
}
|
||||
return savetree;
|
||||
#endif
|
||||
/* find set definitions embedded in query */
|
||||
fixupsets((Query *) lfirst(parse));
|
||||
|
||||
return queryList;
|
||||
}
|
||||
return savetree;
|
||||
#endif
|
||||
|
||||
return queryList;
|
||||
}
|
||||
|
||||
#ifdef SETS_FIXED
|
||||
static void
|
||||
fixupsets(Query *parse)
|
||||
fixupsets(Query * parse)
|
||||
{
|
||||
if (parse == NULL)
|
||||
return;
|
||||
if (parse->commandType==CMD_UTILITY) /* utility */
|
||||
return;
|
||||
if (parse->commandType!=CMD_INSERT)
|
||||
return;
|
||||
define_sets(parse);
|
||||
if (parse == NULL)
|
||||
return;
|
||||
if (parse->commandType == CMD_UTILITY) /* utility */
|
||||
return;
|
||||
if (parse->commandType != CMD_INSERT)
|
||||
return;
|
||||
define_sets(parse);
|
||||
}
|
||||
|
||||
/* Recursively find all of the Consts in the parsetree. Some of
|
||||
* these may represent a set. The value of the Const will be the
|
||||
* query (a string) which defines the set. Call SetDefine to define
|
||||
* query (a string) which defines the set. Call SetDefine to define
|
||||
* the set, and store the OID of the new set in the Const instead.
|
||||
*/
|
||||
static void
|
||||
define_sets(Node *clause)
|
||||
define_sets(Node * clause)
|
||||
{
|
||||
Oid setoid;
|
||||
Type t = type("oid");
|
||||
Oid typeoid = typeid(t);
|
||||
Size oidsize = tlen(t);
|
||||
bool oidbyval = tbyval(t);
|
||||
|
||||
if (clause==NULL) {
|
||||
return;
|
||||
} else if (IsA(clause,LispList)) {
|
||||
define_sets(lfirst(clause));
|
||||
define_sets(lnext(clause));
|
||||
} else if (IsA(clause,Const)) {
|
||||
if (get_constisnull((Const)clause) ||
|
||||
!get_constisset((Const)clause)) {
|
||||
return;
|
||||
Oid setoid;
|
||||
Type t = type("oid");
|
||||
Oid typeoid = typeid(t);
|
||||
Size oidsize = tlen(t);
|
||||
bool oidbyval = tbyval(t);
|
||||
|
||||
if (clause == NULL)
|
||||
{
|
||||
return;
|
||||
}
|
||||
setoid = SetDefine(((Const*)clause)->constvalue,
|
||||
get_id_typname(((Const*)clause)->consttype));
|
||||
set_constvalue((Const)clause, setoid);
|
||||
set_consttype((Const)clause,typeoid);
|
||||
set_constlen((Const)clause,oidsize);
|
||||
set_constbyval((Const)clause,oidbyval);
|
||||
} else if ( IsA(clause,Iter) ) {
|
||||
define_sets(((Iter*)clause)->iterexpr);
|
||||
} else if (single_node (clause)) {
|
||||
return;
|
||||
} else if (or_clause(clause)) {
|
||||
List *temp;
|
||||
/* mapcan */
|
||||
foreach (temp, ((Expr*)clause)->args) {
|
||||
define_sets(lfirst(temp));
|
||||
else if (IsA(clause, LispList))
|
||||
{
|
||||
define_sets(lfirst(clause));
|
||||
define_sets(lnext(clause));
|
||||
}
|
||||
} else if (is_funcclause (clause)) {
|
||||
List *temp;
|
||||
/* mapcan */
|
||||
foreach(temp, ((Expr*)clause)->args) {
|
||||
define_sets(lfirst(temp));
|
||||
else if (IsA(clause, Const))
|
||||
{
|
||||
if (get_constisnull((Const) clause) ||
|
||||
!get_constisset((Const) clause))
|
||||
{
|
||||
return;
|
||||
}
|
||||
setoid = SetDefine(((Const *) clause)->constvalue,
|
||||
get_id_typname(((Const *) clause)->consttype));
|
||||
set_constvalue((Const) clause, setoid);
|
||||
set_consttype((Const) clause, typeoid);
|
||||
set_constlen((Const) clause, oidsize);
|
||||
set_constbyval((Const) clause, oidbyval);
|
||||
}
|
||||
else if (IsA(clause, Iter))
|
||||
{
|
||||
define_sets(((Iter *) clause)->iterexpr);
|
||||
}
|
||||
else if (single_node(clause))
|
||||
{
|
||||
return;
|
||||
}
|
||||
else if (or_clause(clause))
|
||||
{
|
||||
List *temp;
|
||||
|
||||
/* mapcan */
|
||||
foreach(temp, ((Expr *) clause)->args)
|
||||
{
|
||||
define_sets(lfirst(temp));
|
||||
}
|
||||
}
|
||||
else if (is_funcclause(clause))
|
||||
{
|
||||
List *temp;
|
||||
|
||||
/* mapcan */
|
||||
foreach(temp, ((Expr *) clause)->args)
|
||||
{
|
||||
define_sets(lfirst(temp));
|
||||
}
|
||||
}
|
||||
else if (IsA(clause, ArrayRef))
|
||||
{
|
||||
define_sets(((ArrayRef *) clause)->refassgnexpr);
|
||||
}
|
||||
else if (not_clause(clause))
|
||||
{
|
||||
define_sets(get_notclausearg(clause));
|
||||
}
|
||||
else if (is_opclause(clause))
|
||||
{
|
||||
define_sets(get_leftop(clause));
|
||||
define_sets(get_rightop(clause));
|
||||
}
|
||||
} else if (IsA(clause,ArrayRef)) {
|
||||
define_sets(((ArrayRef*)clause)->refassgnexpr);
|
||||
} else if (not_clause (clause)) {
|
||||
define_sets (get_notclausearg (clause));
|
||||
} else if (is_opclause (clause)) {
|
||||
define_sets(get_leftop (clause));
|
||||
define_sets(get_rightop (clause));
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
/* not used
|
||||
#define PSIZE(PTR) (*((int32 *)(PTR) - 1))
|
||||
#define PSIZE(PTR) (*((int32 *)(PTR) - 1))
|
||||
*/
|
||||
|
||||
Node *
|
||||
parser_typecast(Value *expr, TypeName *typename, int typlen)
|
||||
Node *
|
||||
parser_typecast(Value * expr, TypeName * typename, int typlen)
|
||||
{
|
||||
/* check for passing non-ints */
|
||||
Const *adt;
|
||||
Datum lcp;
|
||||
Type tp;
|
||||
char type_string[16];
|
||||
int32 len;
|
||||
char *cp = NULL;
|
||||
char *const_string = NULL;
|
||||
bool string_palloced = false;
|
||||
/* check for passing non-ints */
|
||||
Const *adt;
|
||||
Datum lcp;
|
||||
Type tp;
|
||||
char type_string[16];
|
||||
int32 len;
|
||||
char *cp = NULL;
|
||||
char *const_string = NULL;
|
||||
bool string_palloced = false;
|
||||
|
||||
switch(nodeTag(expr)) {
|
||||
case T_String:
|
||||
const_string = DatumGetPointer(expr->val.str);
|
||||
break;
|
||||
case T_Integer:
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string, "%d", expr->val.ival);
|
||||
break;
|
||||
default:
|
||||
elog(WARN,
|
||||
"parser_typecast: cannot cast this expression to type \"%s\"",
|
||||
typename->name);
|
||||
}
|
||||
switch (nodeTag(expr))
|
||||
{
|
||||
case T_String:
|
||||
const_string = DatumGetPointer(expr->val.str);
|
||||
break;
|
||||
case T_Integer:
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string, "%d", expr->val.ival);
|
||||
break;
|
||||
default:
|
||||
elog(WARN,
|
||||
"parser_typecast: cannot cast this expression to type \"%s\"",
|
||||
typename->name);
|
||||
}
|
||||
|
||||
if (typename->arrayBounds != NIL) {
|
||||
sprintf(type_string,"_%s", typename->name);
|
||||
tp = (Type) type(type_string);
|
||||
} else {
|
||||
tp = (Type) type(typename->name);
|
||||
}
|
||||
|
||||
len = tlen(tp);
|
||||
|
||||
#if 0 /* fix me */
|
||||
switch ( CInteger(lfirst(expr)) ) {
|
||||
case INT4OID: /* int4 */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string,"%d", ((Const*)lnext(expr))->constvalue);
|
||||
break;
|
||||
|
||||
case NAMEOID: /* char16 */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string,"%s", ((Const*)lnext(expr))->constvalue);
|
||||
break;
|
||||
|
||||
case CHAROID: /* char */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string,"%c", ((Const)lnext(expr))->constvalue);
|
||||
break;
|
||||
|
||||
case FLOAT8OID:/* float8 */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string,"%f", ((Const)lnext(expr))->constvalue);
|
||||
break;
|
||||
if (typename->arrayBounds != NIL)
|
||||
{
|
||||
sprintf(type_string, "_%s", typename->name);
|
||||
tp = (Type) type(type_string);
|
||||
}
|
||||
else
|
||||
{
|
||||
tp = (Type) type(typename->name);
|
||||
}
|
||||
|
||||
case CASHOID: /* money */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string,"%d",
|
||||
(int) ((Const*)expr)->constvalue);
|
||||
break;
|
||||
|
||||
case TEXTOID: /* text */
|
||||
const_string = DatumGetPointer(((Const)lnext(expr))->constvalue);
|
||||
const_string = (char *) textout((struct varlena *)const_string);
|
||||
break;
|
||||
|
||||
case UNKNOWNOID: /* unknown */
|
||||
const_string = DatumGetPointer(((Const)lnext(expr))->constvalue);
|
||||
const_string = (char *) textout((struct varlena *)const_string);
|
||||
break;
|
||||
|
||||
default:
|
||||
elog(WARN,"unknown type %d", CInteger(lfirst(expr)));
|
||||
}
|
||||
len = tlen(tp);
|
||||
|
||||
#if 0 /* fix me */
|
||||
switch (CInteger(lfirst(expr)))
|
||||
{
|
||||
case INT4OID: /* int4 */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string, "%d", ((Const *) lnext(expr))->constvalue);
|
||||
break;
|
||||
|
||||
case NAMEOID: /* char16 */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string, "%s", ((Const *) lnext(expr))->constvalue);
|
||||
break;
|
||||
|
||||
case CHAROID: /* char */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string, "%c", ((Const) lnext(expr))->constvalue);
|
||||
break;
|
||||
|
||||
case FLOAT8OID: /* float8 */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string, "%f", ((Const) lnext(expr))->constvalue);
|
||||
break;
|
||||
|
||||
case CASHOID: /* money */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string, "%d",
|
||||
(int) ((Const *) expr)->constvalue);
|
||||
break;
|
||||
|
||||
case TEXTOID: /* text */
|
||||
const_string = DatumGetPointer(((Const) lnext(expr))->constvalue);
|
||||
const_string = (char *) textout((struct varlena *) const_string);
|
||||
break;
|
||||
|
||||
case UNKNOWNOID: /* unknown */
|
||||
const_string = DatumGetPointer(((Const) lnext(expr))->constvalue);
|
||||
const_string = (char *) textout((struct varlena *) const_string);
|
||||
break;
|
||||
|
||||
default:
|
||||
elog(WARN, "unknown type %d", CInteger(lfirst(expr)));
|
||||
}
|
||||
#endif
|
||||
|
||||
cp = instr2 (tp, const_string, typlen);
|
||||
|
||||
if (!tbyvalue(tp)) {
|
||||
/*
|
||||
if (len >= 0 && len != PSIZE(cp)) {
|
||||
char *pp;
|
||||
pp = (char *) palloc(len);
|
||||
memmove(pp, cp, len);
|
||||
cp = pp;
|
||||
}
|
||||
*/
|
||||
lcp = PointerGetDatum(cp);
|
||||
} else {
|
||||
switch(len) {
|
||||
case 1:
|
||||
lcp = Int8GetDatum(cp);
|
||||
break;
|
||||
case 2:
|
||||
lcp = Int16GetDatum(cp);
|
||||
break;
|
||||
case 4:
|
||||
lcp = Int32GetDatum(cp);
|
||||
break;
|
||||
default:
|
||||
lcp = PointerGetDatum(cp);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
adt = makeConst(typeid(tp),
|
||||
len,
|
||||
(Datum)lcp ,
|
||||
false,
|
||||
tbyvalue(tp),
|
||||
false, /* not a set */
|
||||
true /* is cast */);
|
||||
|
||||
if (string_palloced)
|
||||
pfree(const_string);
|
||||
|
||||
return (Node*)adt;
|
||||
}
|
||||
cp = instr2(tp, const_string, typlen);
|
||||
|
||||
Node *
|
||||
parser_typecast2(Node *expr, Oid exprType, Type tp, int typlen)
|
||||
{
|
||||
/* check for passing non-ints */
|
||||
Const *adt;
|
||||
Datum lcp;
|
||||
int32 len = tlen(tp);
|
||||
char *cp = NULL;
|
||||
|
||||
char *const_string = NULL;
|
||||
bool string_palloced = false;
|
||||
|
||||
Assert(IsA(expr,Const));
|
||||
|
||||
switch (exprType) {
|
||||
case 0: /* NULL */
|
||||
break;
|
||||
case INT4OID: /* int4 */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string,"%d",
|
||||
(int) ((Const*)expr)->constvalue);
|
||||
break;
|
||||
case NAMEOID: /* char16 */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string,"%s",
|
||||
(char*) ((Const*)expr)->constvalue);
|
||||
break;
|
||||
case CHAROID: /* char */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string,"%c",
|
||||
(char) ((Const*)expr)->constvalue);
|
||||
break;
|
||||
case FLOAT4OID: /* float4 */
|
||||
if (!tbyvalue(tp))
|
||||
{
|
||||
float32 floatVal =
|
||||
DatumGetFloat32(((Const*)expr)->constvalue);
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string,"%f", *floatVal);
|
||||
break;
|
||||
}
|
||||
case FLOAT8OID:/* float8 */
|
||||
{
|
||||
float64 floatVal =
|
||||
DatumGetFloat64(((Const*)expr)->constvalue);
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string,"%f", *floatVal);
|
||||
break;
|
||||
}
|
||||
case CASHOID: /* money */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string,"%d",
|
||||
(long) ((Const*)expr)->constvalue);
|
||||
break;
|
||||
case TEXTOID: /* text */
|
||||
const_string =
|
||||
DatumGetPointer(((Const*)expr)->constvalue );
|
||||
const_string = (char *) textout((struct varlena *)const_string);
|
||||
break;
|
||||
case UNKNOWNOID: /* unknown */
|
||||
const_string =
|
||||
DatumGetPointer(((Const*)expr)->constvalue );
|
||||
const_string = (char *) textout((struct varlena *)const_string);
|
||||
break;
|
||||
default:
|
||||
elog(WARN,"unknown type %u ",exprType);
|
||||
}
|
||||
|
||||
if (!exprType) {
|
||||
adt = makeConst(typeid(tp),
|
||||
(Size) 0,
|
||||
(Datum) NULL,
|
||||
true, /* isnull */
|
||||
false, /* was omitted */
|
||||
false, /* not a set */
|
||||
true /* is cast */);
|
||||
return ((Node*) adt);
|
||||
}
|
||||
|
||||
cp = instr2 (tp, const_string, typlen);
|
||||
|
||||
|
||||
if (!tbyvalue(tp)) {
|
||||
/*
|
||||
if (len >= 0 && len != PSIZE(cp)) {
|
||||
char *pp;
|
||||
pp = (char *) palloc(len);
|
||||
memmove(pp, cp, len);
|
||||
cp = pp;
|
||||
}
|
||||
if (len >= 0 && len != PSIZE(cp)) {
|
||||
char *pp;
|
||||
pp = (char *) palloc(len);
|
||||
memmove(pp, cp, len);
|
||||
cp = pp;
|
||||
}
|
||||
*/
|
||||
lcp = PointerGetDatum(cp);
|
||||
} else {
|
||||
switch(len) {
|
||||
case 1:
|
||||
lcp = Int8GetDatum(cp);
|
||||
break;
|
||||
case 2:
|
||||
lcp = Int16GetDatum(cp);
|
||||
break;
|
||||
case 4:
|
||||
lcp = Int32GetDatum(cp);
|
||||
break;
|
||||
default:
|
||||
lcp = PointerGetDatum(cp);
|
||||
break;
|
||||
lcp = PointerGetDatum(cp);
|
||||
}
|
||||
}
|
||||
|
||||
adt = makeConst(typeid(tp),
|
||||
(Size)len,
|
||||
(Datum)lcp,
|
||||
false,
|
||||
false, /*was omitted*/
|
||||
false, /* not a set */
|
||||
true /* is cast */);
|
||||
/*
|
||||
printf("adt %s : %u %d %d\n",CString(expr),typeid(tp) ,
|
||||
len,cp);
|
||||
*/
|
||||
if (string_palloced) pfree(const_string);
|
||||
|
||||
return ((Node*) adt);
|
||||
}
|
||||
|
||||
Aggreg *
|
||||
ParseAgg(char *aggname, Oid basetype, Node *target)
|
||||
{
|
||||
Oid fintype;
|
||||
Oid vartype;
|
||||
Oid xfn1;
|
||||
Form_pg_aggregate aggform;
|
||||
Aggreg *aggreg;
|
||||
HeapTuple theAggTuple;
|
||||
|
||||
theAggTuple = SearchSysCacheTuple(AGGNAME, PointerGetDatum(aggname),
|
||||
ObjectIdGetDatum(basetype),
|
||||
0, 0);
|
||||
if (!HeapTupleIsValid(theAggTuple)) {
|
||||
elog(WARN, "aggregate %s does not exist", aggname);
|
||||
}
|
||||
|
||||
aggform = (Form_pg_aggregate) GETSTRUCT(theAggTuple);
|
||||
fintype = aggform->aggfinaltype;
|
||||
xfn1 = aggform->aggtransfn1;
|
||||
|
||||
if (nodeTag(target) != T_Var && nodeTag(target) != T_Expr)
|
||||
elog(WARN, "parser: aggregate can only be applied on an attribute or expression");
|
||||
|
||||
/* only aggregates with transfn1 need a base type */
|
||||
if (OidIsValid(xfn1)) {
|
||||
basetype = aggform->aggbasetype;
|
||||
if (nodeTag(target) == T_Var)
|
||||
vartype = ((Var*)target)->vartype;
|
||||
else
|
||||
vartype = ((Expr*)target)->typeOid;
|
||||
{
|
||||
switch (len)
|
||||
{
|
||||
case 1:
|
||||
lcp = Int8GetDatum(cp);
|
||||
break;
|
||||
case 2:
|
||||
lcp = Int16GetDatum(cp);
|
||||
break;
|
||||
case 4:
|
||||
lcp = Int32GetDatum(cp);
|
||||
break;
|
||||
default:
|
||||
lcp = PointerGetDatum(cp);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (basetype != vartype) {
|
||||
Type tp1, tp2;
|
||||
|
||||
tp1 = get_id_type(basetype);
|
||||
tp2 = get_id_type(vartype);
|
||||
elog(NOTICE, "Aggregate type mismatch:");
|
||||
elog(WARN, "%s works on %s, not %s", aggname,
|
||||
tname(tp1), tname(tp2));
|
||||
}
|
||||
}
|
||||
adt = makeConst(typeid(tp),
|
||||
len,
|
||||
(Datum) lcp,
|
||||
false,
|
||||
tbyvalue(tp),
|
||||
false, /* not a set */
|
||||
true /* is cast */ );
|
||||
|
||||
aggreg = makeNode(Aggreg);
|
||||
aggreg->aggname = pstrdup(aggname);
|
||||
aggreg->basetype = aggform->aggbasetype;
|
||||
aggreg->aggtype = fintype;
|
||||
if (string_palloced)
|
||||
pfree(const_string);
|
||||
|
||||
aggreg->target = target;
|
||||
|
||||
return aggreg;
|
||||
return (Node *) adt;
|
||||
}
|
||||
|
||||
Node *
|
||||
parser_typecast2(Node * expr, Oid exprType, Type tp, int typlen)
|
||||
{
|
||||
/* check for passing non-ints */
|
||||
Const *adt;
|
||||
Datum lcp;
|
||||
int32 len = tlen(tp);
|
||||
char *cp = NULL;
|
||||
|
||||
char *const_string = NULL;
|
||||
bool string_palloced = false;
|
||||
|
||||
Assert(IsA(expr, Const));
|
||||
|
||||
switch (exprType)
|
||||
{
|
||||
case 0: /* NULL */
|
||||
break;
|
||||
case INT4OID: /* int4 */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string, "%d",
|
||||
(int) ((Const *) expr)->constvalue);
|
||||
break;
|
||||
case NAMEOID: /* char16 */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string, "%s",
|
||||
(char *) ((Const *) expr)->constvalue);
|
||||
break;
|
||||
case CHAROID: /* char */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string, "%c",
|
||||
(char) ((Const *) expr)->constvalue);
|
||||
break;
|
||||
case FLOAT4OID: /* float4 */
|
||||
{
|
||||
float32 floatVal =
|
||||
DatumGetFloat32(((Const *) expr)->constvalue);
|
||||
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string, "%f", *floatVal);
|
||||
break;
|
||||
}
|
||||
case FLOAT8OID: /* float8 */
|
||||
{
|
||||
float64 floatVal =
|
||||
DatumGetFloat64(((Const *) expr)->constvalue);
|
||||
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string, "%f", *floatVal);
|
||||
break;
|
||||
}
|
||||
case CASHOID: /* money */
|
||||
const_string = (char *) palloc(256);
|
||||
string_palloced = true;
|
||||
sprintf(const_string, "%d",
|
||||
(long) ((Const *) expr)->constvalue);
|
||||
break;
|
||||
case TEXTOID: /* text */
|
||||
const_string =
|
||||
DatumGetPointer(((Const *) expr)->constvalue);
|
||||
const_string = (char *) textout((struct varlena *) const_string);
|
||||
break;
|
||||
case UNKNOWNOID: /* unknown */
|
||||
const_string =
|
||||
DatumGetPointer(((Const *) expr)->constvalue);
|
||||
const_string = (char *) textout((struct varlena *) const_string);
|
||||
break;
|
||||
default:
|
||||
elog(WARN, "unknown type %u ", exprType);
|
||||
}
|
||||
|
||||
if (!exprType)
|
||||
{
|
||||
adt = makeConst(typeid(tp),
|
||||
(Size) 0,
|
||||
(Datum) NULL,
|
||||
true, /* isnull */
|
||||
false, /* was omitted */
|
||||
false, /* not a set */
|
||||
true /* is cast */ );
|
||||
return ((Node *) adt);
|
||||
}
|
||||
|
||||
cp = instr2(tp, const_string, typlen);
|
||||
|
||||
|
||||
if (!tbyvalue(tp))
|
||||
{
|
||||
/*
|
||||
if (len >= 0 && len != PSIZE(cp)) {
|
||||
char *pp;
|
||||
pp = (char *) palloc(len);
|
||||
memmove(pp, cp, len);
|
||||
cp = pp;
|
||||
}
|
||||
*/
|
||||
lcp = PointerGetDatum(cp);
|
||||
}
|
||||
else
|
||||
{
|
||||
switch (len)
|
||||
{
|
||||
case 1:
|
||||
lcp = Int8GetDatum(cp);
|
||||
break;
|
||||
case 2:
|
||||
lcp = Int16GetDatum(cp);
|
||||
break;
|
||||
case 4:
|
||||
lcp = Int32GetDatum(cp);
|
||||
break;
|
||||
default:
|
||||
lcp = PointerGetDatum(cp);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
adt = makeConst(typeid(tp),
|
||||
(Size) len,
|
||||
(Datum) lcp,
|
||||
false,
|
||||
false, /* was omitted */
|
||||
false, /* not a set */
|
||||
true /* is cast */ );
|
||||
|
||||
/*
|
||||
* printf("adt %s : %u %d %d\n",CString(expr),typeid(tp) , len,cp);
|
||||
*/
|
||||
if (string_palloced)
|
||||
pfree(const_string);
|
||||
|
||||
return ((Node *) adt);
|
||||
}
|
||||
|
||||
Aggreg *
|
||||
ParseAgg(char *aggname, Oid basetype, Node * target)
|
||||
{
|
||||
Oid fintype;
|
||||
Oid vartype;
|
||||
Oid xfn1;
|
||||
Form_pg_aggregate aggform;
|
||||
Aggreg *aggreg;
|
||||
HeapTuple theAggTuple;
|
||||
|
||||
theAggTuple = SearchSysCacheTuple(AGGNAME, PointerGetDatum(aggname),
|
||||
ObjectIdGetDatum(basetype),
|
||||
0, 0);
|
||||
if (!HeapTupleIsValid(theAggTuple))
|
||||
{
|
||||
elog(WARN, "aggregate %s does not exist", aggname);
|
||||
}
|
||||
|
||||
aggform = (Form_pg_aggregate) GETSTRUCT(theAggTuple);
|
||||
fintype = aggform->aggfinaltype;
|
||||
xfn1 = aggform->aggtransfn1;
|
||||
|
||||
if (nodeTag(target) != T_Var && nodeTag(target) != T_Expr)
|
||||
elog(WARN, "parser: aggregate can only be applied on an attribute or expression");
|
||||
|
||||
/* only aggregates with transfn1 need a base type */
|
||||
if (OidIsValid(xfn1))
|
||||
{
|
||||
basetype = aggform->aggbasetype;
|
||||
if (nodeTag(target) == T_Var)
|
||||
vartype = ((Var *) target)->vartype;
|
||||
else
|
||||
vartype = ((Expr *) target)->typeOid;
|
||||
|
||||
if (basetype != vartype)
|
||||
{
|
||||
Type tp1,
|
||||
tp2;
|
||||
|
||||
tp1 = get_id_type(basetype);
|
||||
tp2 = get_id_type(vartype);
|
||||
elog(NOTICE, "Aggregate type mismatch:");
|
||||
elog(WARN, "%s works on %s, not %s", aggname,
|
||||
tname(tp1), tname(tp2));
|
||||
}
|
||||
}
|
||||
|
||||
aggreg = makeNode(Aggreg);
|
||||
aggreg->aggname = pstrdup(aggname);
|
||||
aggreg->basetype = aggform->aggbasetype;
|
||||
aggreg->aggtype = fintype;
|
||||
|
||||
aggreg->target = target;
|
||||
|
||||
return aggreg;
|
||||
}
|
||||
|
||||
@@ -1,14 +1,14 @@
|
||||
/*-------------------------------------------------------------------------
|
||||
*
|
||||
* scansup.c--
|
||||
* support routines for the lex/flex scanner, used by both the normal
|
||||
* support routines for the lex/flex scanner, used by both the normal
|
||||
* backend as well as the bootstrap backend
|
||||
*
|
||||
* Copyright (c) 1994, Regents of the University of California
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/parser/scansup.c,v 1.5 1996/11/15 18:38:55 momjian Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/parser/scansup.c,v 1.6 1997/09/07 04:44:51 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@@ -24,12 +24,12 @@
|
||||
#include "parser/scansup.h"
|
||||
|
||||
/* ----------------
|
||||
* scanstr
|
||||
*
|
||||
* scanstr
|
||||
*
|
||||
* if the string passed in has escaped codes, map the escape codes to actual
|
||||
* chars
|
||||
*
|
||||
* also, remove leading and ending quotes '"' if any
|
||||
* also, remove leading and ending quotes '"' if any
|
||||
*
|
||||
* the string passed in must be non-null
|
||||
*
|
||||
@@ -38,88 +38,95 @@
|
||||
* ----------------
|
||||
*/
|
||||
|
||||
char*
|
||||
char *
|
||||
scanstr(char *s)
|
||||
{
|
||||
static char newStr[MAX_PARSE_BUFFER];
|
||||
int len, i, j;
|
||||
|
||||
if (s == NULL || s[0] == '\0')
|
||||
return s;
|
||||
static char newStr[MAX_PARSE_BUFFER];
|
||||
int len,
|
||||
i,
|
||||
j;
|
||||
|
||||
len = strlen(s);
|
||||
if (s == NULL || s[0] == '\0')
|
||||
return s;
|
||||
|
||||
for (i = 0, j = 0; i < len ; i++) {
|
||||
if (s[i] == '\'') {
|
||||
i = i + 1;
|
||||
if (s[i] == '\'')
|
||||
newStr[j] = '\'';
|
||||
len = strlen(s);
|
||||
|
||||
for (i = 0, j = 0; i < len; i++)
|
||||
{
|
||||
if (s[i] == '\'')
|
||||
{
|
||||
i = i + 1;
|
||||
if (s[i] == '\'')
|
||||
newStr[j] = '\'';
|
||||
}
|
||||
else
|
||||
{
|
||||
if (s[i] == '\\')
|
||||
{
|
||||
i = i + 1;
|
||||
switch (s[i])
|
||||
{
|
||||
case '\\':
|
||||
newStr[j] = '\\';
|
||||
break;
|
||||
case 'b':
|
||||
newStr[j] = '\b';
|
||||
break;
|
||||
case 'f':
|
||||
newStr[j] = '\f';
|
||||
break;
|
||||
case 'n':
|
||||
newStr[j] = '\n';
|
||||
break;
|
||||
case 'r':
|
||||
newStr[j] = '\r';
|
||||
break;
|
||||
case 't':
|
||||
newStr[j] = '\t';
|
||||
break;
|
||||
case '"':
|
||||
newStr[j] = '"';
|
||||
break;
|
||||
case '\'':
|
||||
newStr[j] = '\'';
|
||||
break;
|
||||
case '0':
|
||||
case '1':
|
||||
case '2':
|
||||
case '3':
|
||||
case '4':
|
||||
case '5':
|
||||
case '6':
|
||||
case '7':
|
||||
{
|
||||
char octal[4];
|
||||
int k;
|
||||
long octVal;
|
||||
|
||||
for (k = 0;
|
||||
s[i + k] >= '0' && s[i + k] <= '7' && k < 3;
|
||||
k++)
|
||||
octal[k] = s[i + k];
|
||||
i += k - 1;
|
||||
octal[3] = '\0';
|
||||
|
||||
octVal = strtol(octal, 0, 8);
|
||||
/* elog (NOTICE, "octal = %s octVal = %d, %od", octal, octVal, octVal);*/
|
||||
if (octVal <= 0377)
|
||||
{
|
||||
newStr[j] = ((char) octVal);
|
||||
break;
|
||||
}
|
||||
}
|
||||
default:
|
||||
newStr[j] = s[i];
|
||||
} /* switch */
|
||||
} /* s[i] == '\\' */
|
||||
else
|
||||
newStr[j] = s[i];
|
||||
}
|
||||
j++;
|
||||
}
|
||||
else {
|
||||
if (s[i] == '\\') {
|
||||
i = i + 1;
|
||||
switch (s[i]) {
|
||||
case '\\':
|
||||
newStr[j] = '\\';
|
||||
break;
|
||||
case 'b':
|
||||
newStr[j] = '\b';
|
||||
break;
|
||||
case 'f':
|
||||
newStr[j] = '\f';
|
||||
break;
|
||||
case 'n':
|
||||
newStr[j] = '\n';
|
||||
break;
|
||||
case 'r':
|
||||
newStr[j] = '\r';
|
||||
break;
|
||||
case 't':
|
||||
newStr[j] = '\t';
|
||||
break;
|
||||
case '"':
|
||||
newStr[j] = '"';
|
||||
break;
|
||||
case '\'':
|
||||
newStr[j] = '\'';
|
||||
break;
|
||||
case '0':
|
||||
case '1':
|
||||
case '2':
|
||||
case '3':
|
||||
case '4':
|
||||
case '5':
|
||||
case '6':
|
||||
case '7':
|
||||
{
|
||||
char octal[4];
|
||||
int k;
|
||||
long octVal;
|
||||
|
||||
for (k=0;
|
||||
s[i+k] >= '0' && s[i+k] <= '7' && k < 3;
|
||||
k++)
|
||||
octal[k] = s[i+k];
|
||||
i += k-1;
|
||||
octal[3] = '\0';
|
||||
|
||||
octVal = strtol(octal,0,8);
|
||||
/* elog (NOTICE, "octal = %s octVal = %d, %od", octal, octVal, octVal);*/
|
||||
if (octVal <= 0377) {
|
||||
newStr[j] = ((char)octVal);
|
||||
break;
|
||||
}
|
||||
}
|
||||
default:
|
||||
newStr[j] = s[i];
|
||||
} /* switch */
|
||||
} /* s[i] == '\\' */
|
||||
else
|
||||
newStr[j] = s[i];
|
||||
}
|
||||
j++;
|
||||
}
|
||||
newStr[j] = '\0';
|
||||
return newStr;
|
||||
newStr[j] = '\0';
|
||||
return newStr;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,14 +1,14 @@
|
||||
/*-------------------------------------------------------------------------
|
||||
*
|
||||
*
|
||||
* sysfunc.c--
|
||||
* process system functions and return a string result
|
||||
*
|
||||
* process system functions and return a string result
|
||||
*
|
||||
* Notes:
|
||||
* 1) I return a string result because most of the functions cannot return any
|
||||
* normal type anyway (e.g. SYS_DATE, SYS_TIME, etc...), and the few that
|
||||
* might (SYS_UID or whatever) can just return it as a string - no problem.
|
||||
* This keeps the function flexible enough to be of good use.
|
||||
*
|
||||
* normal type anyway (e.g. SYS_DATE, SYS_TIME, etc...), and the few that
|
||||
* might (SYS_UID or whatever) can just return it as a string - no problem.
|
||||
* This keeps the function flexible enough to be of good use.
|
||||
*
|
||||
* Written by Chad Robinson, chadr@brttech.com
|
||||
* Last modified: 04/27/1996
|
||||
* -------------------------------------------------------------------------
|
||||
@@ -27,39 +27,42 @@
|
||||
* Can't get much more obvious than this. Might need to replace localtime()
|
||||
* on older systems...
|
||||
*/
|
||||
static char *Sysfunc_system_date(void)
|
||||
static char *
|
||||
Sysfunc_system_date(void)
|
||||
{
|
||||
time_t cur_time_secs;
|
||||
struct tm *cur_time_expanded;
|
||||
static char buf[12]; /* Just for safety, y'understand... */
|
||||
|
||||
time_t cur_time_secs;
|
||||
struct tm *cur_time_expanded;
|
||||
static char buf[12]; /* Just for safety, y'understand... */
|
||||
|
||||
time(&cur_time_secs);
|
||||
cur_time_expanded = localtime(&cur_time_secs);
|
||||
if (EuroDates == 1)
|
||||
sprintf(buf, "%2.2d-%2.2d-%4.4d", cur_time_expanded->tm_mday,
|
||||
cur_time_expanded->tm_mon+1, cur_time_expanded->tm_year+1900);
|
||||
cur_time_expanded->tm_mon + 1, cur_time_expanded->tm_year + 1900);
|
||||
else
|
||||
sprintf(buf, "%2.2d-%2.2d-%4.4d", cur_time_expanded->tm_mon+1,
|
||||
cur_time_expanded->tm_mday, cur_time_expanded->tm_year+1900);
|
||||
sprintf(buf, "%2.2d-%2.2d-%4.4d", cur_time_expanded->tm_mon + 1,
|
||||
cur_time_expanded->tm_mday, cur_time_expanded->tm_year + 1900);
|
||||
|
||||
return &buf[0];
|
||||
}
|
||||
|
||||
static char *Sysfunc_system_time(void)
|
||||
static char *
|
||||
Sysfunc_system_time(void)
|
||||
{
|
||||
time_t cur_time_secs;
|
||||
struct tm *cur_time_expanded;
|
||||
static char buf[10]; /* Just for safety, y'understand... */
|
||||
|
||||
time_t cur_time_secs;
|
||||
struct tm *cur_time_expanded;
|
||||
static char buf[10]; /* Just for safety, y'understand... */
|
||||
|
||||
time(&cur_time_secs);
|
||||
cur_time_expanded = localtime(&cur_time_secs);
|
||||
sprintf(buf, "%2.2d:%2.2d:%2.2d", cur_time_expanded->tm_hour,
|
||||
cur_time_expanded->tm_min, cur_time_expanded->tm_sec);
|
||||
cur_time_expanded->tm_min, cur_time_expanded->tm_sec);
|
||||
|
||||
return &buf[0];
|
||||
}
|
||||
|
||||
char *SystemFunctionHandler(char *funct)
|
||||
char *
|
||||
SystemFunctionHandler(char *funct)
|
||||
{
|
||||
if (!strcmp(funct, "SYS_DATE"))
|
||||
return Sysfunc_system_date();
|
||||
@@ -73,9 +76,11 @@ char *SystemFunctionHandler(char *funct)
|
||||
* Chad's rule of coding #4 - never delete a test function, even a stupid
|
||||
* one - you always need it 10 minutes after you delete it.
|
||||
*/
|
||||
void main(void)
|
||||
void
|
||||
main(void)
|
||||
{
|
||||
printf("Current system date: %s\n", SystemFunctionHandler("SYS_DATE"));
|
||||
return;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
Reference in New Issue
Block a user