Skip to content

Commit def0ac2

Browse files
committed
Merge branch 'pgpro-1376'
2 parents 8371dbf + 3b3e55b commit def0ac2

File tree

6 files changed

+386
-405
lines changed

6 files changed

+386
-405
lines changed

src/backup.c

Lines changed: 50 additions & 225 deletions
Original file line numberDiff line numberDiff line change
@@ -99,6 +99,7 @@ static void pg_switch_wal(PGconn *conn);
9999
static void pg_stop_backup(pgBackup *backup);
100100
static int checkpoint_timeout(void);
101101

102+
//static void backup_list_file(parray *files, const char *root, )
102103
static void parse_backup_filelist_filenames(parray *files, const char *root);
103104
static void write_backup_file_list(parray *files, const char *root);
104105
static void wait_wal_lsn(XLogRecPtr lsn, bool wait_prev_segment);
@@ -273,7 +274,8 @@ ReceiveFileList(parray* files, PGconn *conn, PGresult *res, int rownum)
273274

274275
/* read one file via replication protocol
275276
* and write it to the destination subdir in 'backup_path' */
276-
static void remote_copy_file(PGconn *conn, pgFile* file)
277+
static void
278+
remote_copy_file(PGconn *conn, pgFile* file)
277279
{
278280
PGresult *res;
279281
char *copybuf = NULL;
@@ -2095,256 +2097,75 @@ backup_files(void *arg)
20952097
static void
20962098
parse_backup_filelist_filenames(parray *files, const char *root)
20972099
{
2098-
size_t i;
2099-
Oid unlogged_file_reloid = 0;
2100+
size_t i = 0;
2101+
Oid unlogged_file_reloid = 0;
21002102

2101-
for (i = 0; i < parray_num(files); i++)
2103+
while (i < parray_num(files))
21022104
{
21032105
pgFile *file = (pgFile *) parray_get(files, i);
21042106
char *relative;
2105-
char filename[MAXPGPATH];
21062107
int sscanf_result;
21072108

21082109
relative = GetRelativePath(file->path, root);
2109-
filename[0] = '\0';
21102110

2111-
elog(VERBOSE, "-----------------------------------------------------: %s", relative);
2112-
if (path_is_prefix_of_path("global", relative))
2111+
if (S_ISREG(file->mode) &&
2112+
path_is_prefix_of_path(PG_TBLSPC_DIR, relative))
21132113
{
2114-
file->tblspcOid = GLOBALTABLESPACE_OID;
2115-
sscanf_result = sscanf(relative, "global/%s", filename);
2116-
elog(VERBOSE, "global sscanf result: %i", sscanf_result);
2117-
if (strcmp(relative, "global") == 0)
2118-
{
2119-
Assert(S_ISDIR(file->mode));
2120-
elog(VERBOSE, "the global itself, filepath %s", relative);
2121-
file->is_database = true; /* TODO add an explanation */
2122-
}
2123-
else if (sscanf_result == 1)
2124-
{
2125-
elog(VERBOSE, "filename %s, filepath %s", filename, relative);
2126-
}
2127-
}
2128-
else if (path_is_prefix_of_path("base", relative))
2129-
{
2130-
file->tblspcOid = DEFAULTTABLESPACE_OID;
2131-
sscanf_result = sscanf(relative, "base/%u/%s", &(file->dbOid), filename);
2132-
elog(VERBOSE, "base sscanf result: %i", sscanf_result);
2133-
if (strcmp(relative, "base") == 0)
2134-
{
2135-
Assert(S_ISDIR(file->mode));
2136-
elog(VERBOSE, "the base itself, filepath %s", relative);
2137-
}
2138-
else if (sscanf_result == 1)
2139-
{
2140-
Assert(S_ISDIR(file->mode));
2141-
elog(VERBOSE, "dboid %u, filepath %s", file->dbOid, relative);
2142-
file->is_database = true;
2143-
}
2144-
else
2145-
{
2146-
elog(VERBOSE, "dboid %u, filename %s, filepath %s", file->dbOid, filename, relative);
2147-
}
2148-
}
2149-
else if (path_is_prefix_of_path(PG_TBLSPC_DIR, relative))
2150-
{
2151-
char temp_relative_path[MAXPGPATH];
2152-
2153-
sscanf_result = sscanf(relative, "pg_tblspc/%u/%s", &(file->tblspcOid), temp_relative_path);
2154-
elog(VERBOSE, "pg_tblspc sscanf result: %i", sscanf_result);
2155-
2156-
if (strcmp(relative, "pg_tblspc") == 0)
2157-
{
2158-
Assert(S_ISDIR(file->mode));
2159-
elog(VERBOSE, "the pg_tblspc itself, filepath %s", relative);
2160-
}
2161-
else if (sscanf_result == 1)
2162-
{
2163-
Assert(S_ISDIR(file->mode));
2164-
elog(VERBOSE, "tblspcOid %u, filepath %s", file->tblspcOid, relative);
2165-
}
2166-
else
2114+
/*
2115+
* Found file in pg_tblspc/tblsOid/TABLESPACE_VERSION_DIRECTORY
2116+
* Legal only in case of 'pg_compression'
2117+
*/
2118+
if (strcmp(file->name, "pg_compression") == 0)
21672119
{
2168-
/*continue parsing */
2169-
sscanf_result = sscanf(temp_relative_path+strlen(TABLESPACE_VERSION_DIRECTORY)+1, "%u/%s",
2170-
&(file->dbOid), filename);
2171-
elog(VERBOSE, "TABLESPACE_VERSION_DIRECTORY sscanf result: %i", sscanf_result);
2172-
2173-
if (sscanf_result == -1)
2174-
{
2175-
elog(VERBOSE, "The TABLESPACE_VERSION_DIRECTORY itself, filepath %s", relative);
2176-
}
2177-
else if (sscanf_result == 0)
2178-
{
2179-
/* Found file in pg_tblspc/tblsOid/TABLESPACE_VERSION_DIRECTORY
2180-
Legal only in case of 'pg_compression'
2181-
*/
2182-
if (strcmp(file->name, "pg_compression") == 0)
2183-
{
2184-
elog(VERBOSE, "Found pg_compression file in TABLESPACE_VERSION_DIRECTORY, filepath %s", relative);
2185-
/*Set every datafile in tablespace as is_cfs */
2186-
set_cfs_datafiles(files, root, relative, i);
2187-
}
2188-
else
2189-
{
2190-
elog(VERBOSE, "Found illegal file in TABLESPACE_VERSION_DIRECTORY, filepath %s", relative);
2191-
}
2120+
Oid tblspcOid;
2121+
Oid dbOid;
2122+
char tmp_rel_path[MAXPGPATH];
2123+
/*
2124+
* Check that the file is located under
2125+
* TABLESPACE_VERSION_DIRECTORY
2126+
*/
2127+
sscanf_result = sscanf(relative, PG_TBLSPC_DIR "/%u/%s/%u",
2128+
&tblspcOid, tmp_rel_path, &dbOid);
21922129

2193-
}
2194-
else if (sscanf_result == 1)
2195-
{
2196-
Assert(S_ISDIR(file->mode));
2197-
elog(VERBOSE, "dboid %u, filepath %s", file->dbOid, relative);
2198-
file->is_database = true;
2199-
}
2200-
else if (sscanf_result == 2)
2201-
{
2202-
elog(VERBOSE, "dboid %u, filename %s, filepath %s", file->dbOid, filename, relative);
2203-
}
2204-
else
2205-
{
2206-
elog(VERBOSE, "Illegal file filepath %s", relative);
2207-
}
2130+
/* Yes, it is */
2131+
if (sscanf_result == 2 &&
2132+
strcmp(tmp_rel_path, TABLESPACE_VERSION_DIRECTORY) == 0)
2133+
set_cfs_datafiles(files, root, relative, i);
22082134
}
22092135
}
2210-
else
2211-
{
2212-
elog(VERBOSE,"other dir or file, filepath %s", relative);
2213-
}
22142136

2215-
if (strcmp(filename, "ptrack_init") == 0)
2137+
if (S_ISREG(file->mode) && file->tblspcOid != 0 &&
2138+
file->name && file->name[0])
22162139
{
2217-
/* Do not backup ptrack_init files */
2218-
pgFileFree(file);
2219-
parray_remove(files, i);
2220-
i--;
2221-
continue;
2222-
}
2223-
2224-
/* Check files located inside database directories including directory 'global' */
2225-
if (filename[0] != '\0' && file->tblspcOid != 0)
2226-
{
2227-
if (strcmp(filename, "pg_internal.init") == 0)
2228-
{
2229-
/* Do not pg_internal.init files
2230-
* (they contain some cache entries, so it's fine) */
2231-
pgFileFree(file);
2232-
parray_remove(files, i);
2233-
i--;
2234-
continue;
2235-
}
2236-
else if (filename[0] == 't' && isdigit(filename[1]))
2237-
{
2238-
elog(VERBOSE, "temp file, filepath %s", relative);
2239-
/* Do not backup temp files */
2240-
pgFileFree(file);
2241-
parray_remove(files, i);
2242-
i--;
2243-
continue;
2244-
}
2245-
else if (isdigit(filename[0]))
2140+
if (strcmp(file->forkName, "init") == 0)
22462141
{
22472142
/*
2248-
* TODO TODO TODO Files of this type can be compressed by cfs.
2249-
* Check that and do not mark them with 'is_datafile' flag.
2143+
* Do not backup files of unlogged relations.
2144+
* scan filelist backward and exclude these files.
22502145
*/
2251-
char *forkNameptr;
2252-
char suffix[MAXPGPATH];
2146+
int unlogged_file_num = i - 1;
2147+
pgFile *unlogged_file = (pgFile *) parray_get(files,
2148+
unlogged_file_num);
22532149

2254-
forkNameptr = strstr(filename, "_");
2255-
if (forkNameptr != NULL)
2256-
{
2257-
/* auxiliary fork of the relfile */
2258-
sscanf(filename, "%u_%s", &(file->relOid), file->forkName);
2259-
elog(VERBOSE, "relOid %u, forkName %s, filepath %s", file->relOid, file->forkName, relative);
2260-
2261-
/* handle unlogged relations */
2262-
if (strcmp(file->forkName, "init") == 0)
2263-
{
2264-
/*
2265-
* Do not backup files of unlogged relations.
2266-
* scan filelist backward and exclude these files.
2267-
*/
2268-
int unlogged_file_num = i-1;
2269-
pgFile *unlogged_file = (pgFile *) parray_get(files, unlogged_file_num);
2270-
2271-
unlogged_file_reloid = file->relOid;
2272-
2273-
while (unlogged_file_num >= 0 &&
2274-
(unlogged_file_reloid != 0) &&
2275-
(unlogged_file->relOid == unlogged_file_reloid))
2276-
{
2277-
unlogged_file->size = 0;
2278-
pgFileFree(unlogged_file);
2279-
parray_remove(files, unlogged_file_num);
2280-
unlogged_file_num--;
2281-
i--;
2282-
unlogged_file = (pgFile *) parray_get(files, unlogged_file_num);
2283-
}
2284-
}
2285-
else if (strcmp(file->forkName, "ptrack") == 0)
2286-
{
2287-
/* Do not backup ptrack files */
2288-
pgFileFree(file);
2289-
parray_remove(files, i);
2290-
i--;
2291-
}
2292-
else if ((unlogged_file_reloid != 0) &&
2293-
(file->relOid == unlogged_file_reloid))
2294-
{
2295-
/* Do not backup forks of unlogged relations */
2296-
pgFileFree(file);
2297-
parray_remove(files, i);
2298-
i--;
2299-
}
2300-
continue;
2301-
}
2150+
unlogged_file_reloid = file->relOid;
23022151

2303-
sscanf_result = sscanf(filename, "%u.%d.%s", &(file->relOid), &(file->segno), suffix);
2304-
if (sscanf_result == 0)
2152+
while (unlogged_file_num >= 0 &&
2153+
(unlogged_file_reloid != 0) &&
2154+
(unlogged_file->relOid == unlogged_file_reloid))
23052155
{
2306-
elog(ERROR, "cannot parse filepath %s", relative);
2307-
}
2308-
else if (sscanf_result == 1)
2309-
{
2310-
/* first segment of the relfile */
2311-
elog(VERBOSE, "relOid %u, segno %d, filepath %s", file->relOid, 0, relative);
2312-
if (strcmp(relative + strlen(relative) - strlen("cfm"), "cfm") == 0)
2313-
{
2314-
/* reloid.cfm */
2315-
elog(VERBOSE, "Found cfm file %s", relative);
2316-
}
2317-
else
2318-
{
2319-
elog(VERBOSE, "Found first segment of the relfile %s", relative);
2320-
file->is_datafile = true;
2321-
}
2322-
}
2323-
else if (sscanf_result == 2)
2324-
{
2325-
/* not first segment of the relfile */
2326-
elog(VERBOSE, "relOid %u, segno %d, filepath %s", file->relOid, file->segno, relative);
2327-
file->is_datafile = true;
2328-
}
2329-
else
2330-
{
2331-
/*
2332-
* some cfs specific file.
2333-
* It is not datafile, because we cannot read it block by block
2334-
*/
2335-
elog(VERBOSE, "relOid %u, segno %d, suffix %s, filepath %s", file->relOid, file->segno, suffix, relative);
2336-
}
2156+
pgFileFree(unlogged_file);
2157+
parray_remove(files, unlogged_file_num);
23372158

2338-
if ((unlogged_file_reloid != 0) &&
2339-
(file->relOid == unlogged_file_reloid))
2340-
{
2341-
/* Do not backup segments of unlogged files */
2342-
pgFileFree(file);
2343-
parray_remove(files, i);
2159+
unlogged_file_num--;
23442160
i--;
2161+
2162+
unlogged_file = (pgFile *) parray_get(files,
2163+
unlogged_file_num);
23452164
}
23462165
}
23472166
}
2167+
2168+
i++;
23482169
}
23492170
}
23502171

@@ -2617,6 +2438,10 @@ stop_streaming(XLogRecPtr xlogpos, uint32 timeline, bool segment_finished)
26172438
static uint32 prevtimeline = 0;
26182439
static XLogRecPtr prevpos = InvalidXLogRecPtr;
26192440

2441+
/* check for interrupt */
2442+
if (interrupted)
2443+
elog(ERROR, "Interrupted during backup");
2444+
26202445
/* we assume that we get called once at the end of each segment */
26212446
if (segment_finished)
26222447
elog(VERBOSE, _("finished segment at %X/%X (timeline %u)"),

0 commit comments

Comments
 (0)