Skip to content

Commit 7800a71

Browse files
committed
Move some pg_dump function around.
Move functions used only by pg_dump and pg_restore from dumputils.c to a new file, pg_backup_utils.c. dumputils.c is linked into psql and some programs in bin/scripts, so it seems good to keep it slim. The parallel functionality is moved to parallel.c, as is exit_horribly, because the interesting code in exit_horribly is parallel-related. This refactoring gets rid of the on_exit_msg_func function pointer. It was problematic, because a modern gcc version with -Wmissing-format-attribute complained if it wasn't marked with PF_PRINTF_ATTRIBUTE, but the ancient gcc version that Tom Lane's old HP-UX box has didn't accept that attribute on a function pointer, and gave an error. We still use a similar function pointer trick for getLocalPQBuffer() function, to use a thread-local version of that in parallel mode on Windows, but that dodges the problem because it doesn't take printf-like arguments.
1 parent 1cea9bb commit 7800a71

19 files changed

+336
-247
lines changed

src/bin/pg_dump/Makefile

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,8 +19,8 @@ include $(top_builddir)/src/Makefile.global
1919
override CPPFLAGS := -I$(libpq_srcdir) $(CPPFLAGS)
2020

2121
OBJS= pg_backup_archiver.o pg_backup_db.o pg_backup_custom.o \
22-
pg_backup_null.o pg_backup_tar.o parallel.o \
23-
pg_backup_directory.o dumputils.o compress_io.o $(WIN32RES)
22+
pg_backup_null.o pg_backup_tar.o pg_backup_directory.o \
23+
pg_backup_utils.o parallel.o compress_io.o dumputils.o $(WIN32RES)
2424

2525
KEYWRDOBJS = keywords.o kwlookup.o
2626

src/bin/pg_dump/common.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
*-------------------------------------------------------------------------
1515
*/
1616
#include "pg_backup_archiver.h"
17+
#include "pg_backup_utils.h"
1718

1819
#include <ctype.h>
1920

src/bin/pg_dump/compress_io.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@
5353
*/
5454

5555
#include "compress_io.h"
56-
#include "dumputils.h"
56+
#include "pg_backup_utils.h"
5757
#include "parallel.h"
5858

5959
/*----------------------

src/bin/pg_dump/dumputils.c

Lines changed: 14 additions & 194 deletions
Original file line numberDiff line numberDiff line change
@@ -25,21 +25,6 @@
2525
extern const ScanKeyword FEScanKeywords[];
2626
extern const int NumFEScanKeywords;
2727

28-
/* Globals exported by this file */
29-
int quote_all_identifiers = 0;
30-
const char *progname = NULL;
31-
32-
#define MAX_ON_EXIT_NICELY 20
33-
34-
static struct
35-
{
36-
on_exit_nicely_callback function;
37-
void *arg;
38-
} on_exit_nicely_list[MAX_ON_EXIT_NICELY];
39-
40-
static int on_exit_nicely_index;
41-
void (*on_exit_msg_func) (const char *modulename, const char *fmt, va_list ap) = vwrite_msg;
42-
4328
#define supports_grant_options(version) ((version) >= 70400)
4429

4530
static bool parseAclItem(const char *item, const char *type,
@@ -49,68 +34,24 @@ static bool parseAclItem(const char *item, const char *type,
4934
static char *copyAclUserName(PQExpBuffer output, char *input);
5035
static void AddAcl(PQExpBuffer aclbuf, const char *keyword,
5136
const char *subname);
52-
static PQExpBuffer getThreadLocalPQExpBuffer(void);
53-
54-
#ifdef WIN32
55-
static void shutdown_parallel_dump_utils(int code, void *unused);
56-
static bool parallel_init_done = false;
57-
static DWORD tls_index;
58-
static DWORD mainThreadId;
37+
static PQExpBuffer defaultGetLocalPQExpBuffer(void);
5938

60-
static void
61-
shutdown_parallel_dump_utils(int code, void *unused)
62-
{
63-
/* Call the cleanup function only from the main thread */
64-
if (mainThreadId == GetCurrentThreadId())
65-
WSACleanup();
66-
}
67-
#endif
68-
69-
void
70-
init_parallel_dump_utils(void)
71-
{
72-
#ifdef WIN32
73-
if (!parallel_init_done)
74-
{
75-
WSADATA wsaData;
76-
int err;
77-
78-
tls_index = TlsAlloc();
79-
mainThreadId = GetCurrentThreadId();
80-
err = WSAStartup(MAKEWORD(2, 2), &wsaData);
81-
if (err != 0)
82-
{
83-
fprintf(stderr, _("WSAStartup failed: %d\n"), err);
84-
exit_nicely(1);
85-
}
86-
on_exit_nicely(shutdown_parallel_dump_utils, NULL);
87-
parallel_init_done = true;
88-
}
89-
#endif
90-
}
39+
/* Globals exported by this file */
40+
int quote_all_identifiers = 0;
41+
PQExpBuffer (*getLocalPQExpBuffer) (void) = defaultGetLocalPQExpBuffer;
9142

9243
/*
93-
* Non-reentrant but reduces memory leakage. (On Windows the memory leakage
94-
* will be one buffer per thread, which is at least better than one per call).
44+
* Returns a temporary PQExpBuffer, valid until the next call to the function.
45+
* This is used by fmtId and fmtQualifiedId.
46+
*
47+
* Non-reentrant and non-thread-safe but reduces memory leakage. You can
48+
* replace this with a custom version by setting the getLocalPQExpBuffer
49+
* function pointer.
9550
*/
9651
static PQExpBuffer
97-
getThreadLocalPQExpBuffer(void)
52+
defaultGetLocalPQExpBuffer(void)
9853
{
99-
/*
100-
* The Tls code goes awry if we use a static var, so we provide for both
101-
* static and auto, and omit any use of the static var when using Tls.
102-
*/
103-
static PQExpBuffer s_id_return = NULL;
104-
PQExpBuffer id_return;
105-
106-
#ifdef WIN32
107-
if (parallel_init_done)
108-
id_return = (PQExpBuffer) TlsGetValue(tls_index); /* 0 when not set */
109-
else
110-
id_return = s_id_return;
111-
#else
112-
id_return = s_id_return;
113-
#endif
54+
static PQExpBuffer id_return = NULL;
11455

11556
if (id_return) /* first time through? */
11657
{
@@ -121,15 +62,6 @@ getThreadLocalPQExpBuffer(void)
12162
{
12263
/* new buffer */
12364
id_return = createPQExpBuffer();
124-
#ifdef WIN32
125-
if (parallel_init_done)
126-
TlsSetValue(tls_index, id_return);
127-
else
128-
s_id_return = id_return;
129-
#else
130-
s_id_return = id_return;
131-
#endif
132-
13365
}
13466

13567
return id_return;
@@ -144,7 +76,7 @@ getThreadLocalPQExpBuffer(void)
14476
const char *
14577
fmtId(const char *rawid)
14678
{
147-
PQExpBuffer id_return = getThreadLocalPQExpBuffer();
79+
PQExpBuffer id_return = getLocalPQExpBuffer();
14880

14981
const char *cp;
15082
bool need_quotes = false;
@@ -238,7 +170,7 @@ fmtQualifiedId(int remoteVersion, const char *schema, const char *id)
238170
}
239171
appendPQExpBuffer(lcl_pqexp, "%s", fmtId(id));
240172

241-
id_return = getThreadLocalPQExpBuffer();
173+
id_return = getLocalPQExpBuffer();
242174

243175
appendPQExpBuffer(id_return, "%s", lcl_pqexp->data);
244176
destroyPQExpBuffer(lcl_pqexp);
@@ -1278,118 +1210,6 @@ emitShSecLabels(PGconn *conn, PGresult *res, PQExpBuffer buffer,
12781210
}
12791211

12801212

1281-
/*
1282-
* Parse a --section=foo command line argument.
1283-
*
1284-
* Set or update the bitmask in *dumpSections according to arg.
1285-
* dumpSections is initialised as DUMP_UNSECTIONED by pg_dump and
1286-
* pg_restore so they can know if this has even been called.
1287-
*/
1288-
void
1289-
set_dump_section(const char *arg, int *dumpSections)
1290-
{
1291-
/* if this is the first call, clear all the bits */
1292-
if (*dumpSections == DUMP_UNSECTIONED)
1293-
*dumpSections = 0;
1294-
1295-
if (strcmp(arg, "pre-data") == 0)
1296-
*dumpSections |= DUMP_PRE_DATA;
1297-
else if (strcmp(arg, "data") == 0)
1298-
*dumpSections |= DUMP_DATA;
1299-
else if (strcmp(arg, "post-data") == 0)
1300-
*dumpSections |= DUMP_POST_DATA;
1301-
else
1302-
{
1303-
fprintf(stderr, _("%s: unrecognized section name: \"%s\"\n"),
1304-
progname, arg);
1305-
fprintf(stderr, _("Try \"%s --help\" for more information.\n"),
1306-
progname);
1307-
exit_nicely(1);
1308-
}
1309-
}
1310-
1311-
1312-
/*
1313-
* Write a printf-style message to stderr.
1314-
*
1315-
* The program name is prepended, if "progname" has been set.
1316-
* Also, if modulename isn't NULL, that's included too.
1317-
* Note that we'll try to translate the modulename and the fmt string.
1318-
*/
1319-
void
1320-
write_msg(const char *modulename, const char *fmt,...)
1321-
{
1322-
va_list ap;
1323-
1324-
va_start(ap, fmt);
1325-
vwrite_msg(modulename, fmt, ap);
1326-
va_end(ap);
1327-
}
1328-
1329-
/*
1330-
* As write_msg, but pass a va_list not variable arguments.
1331-
*/
1332-
void
1333-
vwrite_msg(const char *modulename, const char *fmt, va_list ap)
1334-
{
1335-
if (progname)
1336-
{
1337-
if (modulename)
1338-
fprintf(stderr, "%s: [%s] ", progname, _(modulename));
1339-
else
1340-
fprintf(stderr, "%s: ", progname);
1341-
}
1342-
vfprintf(stderr, _(fmt), ap);
1343-
}
1344-
1345-
1346-
/*
1347-
* Fail and die, with a message to stderr. Parameters as for write_msg.
1348-
*/
1349-
void
1350-
exit_horribly(const char *modulename, const char *fmt,...)
1351-
{
1352-
va_list ap;
1353-
1354-
va_start(ap, fmt);
1355-
on_exit_msg_func(modulename, fmt, ap);
1356-
va_end(ap);
1357-
1358-
exit_nicely(1);
1359-
}
1360-
1361-
/* Register a callback to be run when exit_nicely is invoked. */
1362-
void
1363-
on_exit_nicely(on_exit_nicely_callback function, void *arg)
1364-
{
1365-
if (on_exit_nicely_index >= MAX_ON_EXIT_NICELY)
1366-
exit_horribly(NULL, "out of on_exit_nicely slots\n");
1367-
on_exit_nicely_list[on_exit_nicely_index].function = function;
1368-
on_exit_nicely_list[on_exit_nicely_index].arg = arg;
1369-
on_exit_nicely_index++;
1370-
}
1371-
1372-
/*
1373-
* Run accumulated on_exit_nicely callbacks in reverse order and then exit
1374-
* quietly. This needs to be thread-safe.
1375-
*/
1376-
void
1377-
exit_nicely(int code)
1378-
{
1379-
int i;
1380-
1381-
for (i = on_exit_nicely_index - 1; i >= 0; i--)
1382-
(*on_exit_nicely_list[i].function) (code,
1383-
on_exit_nicely_list[i].arg);
1384-
1385-
#ifdef WIN32
1386-
if (parallel_init_done && GetCurrentThreadId() != mainThreadId)
1387-
ExitThread(code);
1388-
#endif
1389-
1390-
exit(code);
1391-
}
1392-
13931213
void
13941214
simple_string_list_append(SimpleStringList *list, const char *val)
13951215
{

src/bin/pg_dump/dumputils.h

Lines changed: 1 addition & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -19,14 +19,6 @@
1919
#include "libpq-fe.h"
2020
#include "pqexpbuffer.h"
2121

22-
typedef enum /* bits returned by set_dump_section */
23-
{
24-
DUMP_PRE_DATA = 0x01,
25-
DUMP_DATA = 0x02,
26-
DUMP_POST_DATA = 0x04,
27-
DUMP_UNSECTIONED = 0xff
28-
} DumpSections;
29-
3022
typedef struct SimpleStringListCell
3123
{
3224
struct SimpleStringListCell *next;
@@ -40,14 +32,9 @@ typedef struct SimpleStringList
4032
} SimpleStringList;
4133

4234

43-
typedef void (*on_exit_nicely_callback) (int code, void *arg);
44-
4535
extern int quote_all_identifiers;
46-
extern const char *progname;
47-
extern void (*on_exit_msg_func) (const char *modulename, const char *fmt, va_list ap)
48-
__attribute__((format(PG_PRINTF_ATTRIBUTE, 2, 0)));
36+
extern PQExpBuffer (*getLocalPQExpBuffer) (void);
4937

50-
extern void init_parallel_dump_utils(void);
5138
extern const char *fmtId(const char *identifier);
5239
extern const char *fmtQualifiedId(int remoteVersion,
5340
const char *schema, const char *id);
@@ -79,17 +66,6 @@ extern void buildShSecLabelQuery(PGconn *conn, const char *catalog_name,
7966
extern void emitShSecLabels(PGconn *conn, PGresult *res,
8067
PQExpBuffer buffer, const char *target, const char *objname);
8168
extern void set_dump_section(const char *arg, int *dumpSections);
82-
extern void
83-
write_msg(const char *modulename, const char *fmt,...)
84-
__attribute__((format(PG_PRINTF_ATTRIBUTE, 2, 3)));
85-
extern void
86-
vwrite_msg(const char *modulename, const char *fmt, va_list ap)
87-
__attribute__((format(PG_PRINTF_ATTRIBUTE, 2, 0)));
88-
extern void
89-
exit_horribly(const char *modulename, const char *fmt,...)
90-
__attribute__((format(PG_PRINTF_ATTRIBUTE, 2, 3), noreturn));
91-
extern void on_exit_nicely(on_exit_nicely_callback function, void *arg);
92-
extern void exit_nicely(int code) __attribute__((noreturn));
9369

9470
extern void simple_string_list_append(SimpleStringList *list, const char *val);
9571
extern bool simple_string_list_member(SimpleStringList *list, const char *val);

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy