1/*-------------------------------------------------------------------------
4 * Front-end large object interface
6 * Portions Copyright (c) 1996-2025, PostgreSQL Global Development Group
7 * Portions Copyright (c) 1994, Regents of the University of California
11 * src/interfaces/libpq/fe-lobj.c
13 *-------------------------------------------------------------------------
18 * As unlink/rename are #define'd in port.h (via postgres_fe.h), io.h
19 * must be included first on MS C. Might as well do it for all WIN32's
42 #define LO_BUFSIZE 8192
51 * opens an existing large object
53 * returns the file descriptor for use in later lo_* calls
54 * return -1 upon failure.
90 * closes an existing large object
92 * returns 0 upon success
93 * returns -1 upon failure.
110 &retval, &result_len, 1, argv, 1);
125 * truncates an existing large object to the given size
127 * returns 0 upon success
128 * returns -1 upon failure
141 /* Must check this on-the-fly because it's not there pre-8.3 */
150 * Long ago, somebody thought it'd be a good idea to declare this function
151 * as taking size_t ... but the underlying backend function only accepts a
152 * signed int32 length. So throw error if the given value overflows
153 * int32. (A possible alternative is to automatically redirect the call
154 * to lo_truncate64; but if the caller wanted to rely on that backend
155 * function being available, he could have called lo_truncate64 for
158 if (
len > (
size_t) INT_MAX)
173 &retval, &result_len, 1, argv, 2);
189 * truncates an existing large object to the given size
191 * returns 0 upon success
192 * returns -1 upon failure
222 &retval, &result_len, 1, argv, 2);
238 * read len bytes of the large object into buf
240 * returns the number of bytes read, or -1 on failure.
241 * the CALLER must have allocated enough space to hold the result returned
255 * Long ago, somebody thought it'd be a good idea to declare this function
256 * as taking size_t ... but the underlying backend function only accepts a
257 * signed int32 length. So throw error if the given value overflows
260 if (
len > (
size_t) INT_MAX)
275 (
void *)
buf, &result_len, 0, argv, 2);
290 * write len bytes of buf into the large object fd
292 * returns the number of bytes written, or -1 on failure.
306 * Long ago, somebody thought it'd be a good idea to declare this function
307 * as taking size_t ... but the underlying backend function only accepts a
308 * signed int32 length. So throw error if the given value overflows
311 if (
len > (
size_t) INT_MAX)
326 &retval, &result_len, 1, argv, 2);
341 * change the current read or write location on a large object
367 &retval, &result_len, 1, argv, 3);
382 * change the current read or write location on a large object
409 argv[1].
u.
ptr = (
int *) &offset;
416 (
void *) &retval, &result_len, 0, argv, 3);
431 * create a new large object
432 * the mode is ignored (once upon a time it had a use)
434 * returns the oid of the large object created or
435 * InvalidOid upon failure
452 &retval, &result_len, 1, argv, 1);
467 * create a new large object
468 * if lobjId isn't InvalidOid, it specifies the OID to (attempt to) create
470 * returns the oid of the large object created or
471 * InvalidOid upon failure
484 /* Must check this on-the-fly because it's not there pre-8.1 */
496 &retval, &result_len, 1, argv, 1);
512 * returns the current seek location of the large object
530 &retval, &result_len, 1, argv, 1);
545 * returns the current seek location of the large object
570 (
void *) &retval, &result_len, 0, argv, 1);
604 &retval, &result_len, 1, argv, 1);
619 * imports a file as an (inversion) large object.
621 * returns the oid of that object upon success,
622 * returns InvalidOid upon failure
632 * lo_import_with_oid -
633 * imports a file as an (inversion) large object.
634 * large object id can be specified.
636 * returns the oid of that object upon success,
637 * returns InvalidOid upon failure
660 /* Since this is the beginning of a query cycle, reset the error state */
664 * open the file to be read in
675 * create an inversion object
684 /* we assume lo_create() already set a suitable error message */
692 /* we assume lo_open() already set a suitable error message */
698 * read in from the file and write to the large object
706 * If lo_write() failed, we are now in an aborted transaction so
707 * there's no need for lo_close(); furthermore, if we tried it
708 * we'd overwrite the useful error result with a useless one. So
709 * just nail the doors shut and get out of town.
718 /* We must do lo_close before setting the errorMessage */
719 int save_errno = errno;
723 /* deliberately overwrite any error from lo_close */
727 strerror_r(save_errno, sebuf,
sizeof(sebuf)));
735 /* we assume lo_close() already set a suitable error message */
744 * exports an (inversion) large object.
745 * returns -1 upon failure, 1 if OK
759 * open the large object.
764 /* we assume lo_open() already set a suitable error message */
769 * create the file to be written to
774 /* We must do lo_close before setting the errorMessage */
775 int save_errno = errno;
778 /* deliberately overwrite any error from lo_close */
782 strerror_r(save_errno, sebuf,
sizeof(sebuf)));
787 * read in from the large object and write to the file
794 /* We must do lo_close before setting the errorMessage */
795 int save_errno = errno;
799 /* deliberately overwrite any error from lo_close */
803 strerror_r(save_errno, sebuf,
sizeof(sebuf)));
809 * If lo_read() failed, we are now in an aborted transaction so there's no
810 * need for lo_close(); furthermore, if we tried it we'd overwrite the
811 * useful error result with a useless one. So skip lo_close() if we got a
817 /* assume lo_read() or lo_close() left a suitable error message */
821 /* if we already failed, don't overwrite that msg with a close error */
822 if (
close(
fd) != 0 && result >= 0)
836 * Initialize for a new large-object operation on an existing connection.
837 * Return 0 if OK, -1 on failure.
839 * If we haven't previously done so, we collect the function OIDs from
840 * pg_proc for all functions that are required for large object operations.
852 /* Nothing we can do with no connection */
856 /* Since this is the beginning of a query cycle, reset the error state */
859 /* Nothing else to do if we already collected info */
864 * Allocate the structure to hold the function OIDs. We don't store it
865 * into the PGconn until it's successfully filled.
868 if (lobjfuncs == NULL)
876 * Execute the query to get all the functions at once. (Not all of them
877 * may exist in older server versions.)
879 query =
"select proname, oid from pg_catalog.pg_proc "
894 "and pronamespace = (select oid from pg_catalog.pg_namespace "
895 "where nspname = 'pg_catalog')";
913 * Examine the result and put the OID's into the struct
919 if (strcmp(fname,
"lo_open") == 0)
921 else if (strcmp(fname,
"lo_close") == 0)
923 else if (strcmp(fname,
"lo_creat") == 0)
925 else if (strcmp(fname,
"lo_create") == 0)
927 else if (strcmp(fname,
"lo_unlink") == 0)
929 else if (strcmp(fname,
"lo_lseek") == 0)
931 else if (strcmp(fname,
"lo_lseek64") == 0)
933 else if (strcmp(fname,
"lo_tell") == 0)
935 else if (strcmp(fname,
"lo_tell64") == 0)
937 else if (strcmp(fname,
"lo_truncate") == 0)
939 else if (strcmp(fname,
"lo_truncate64") == 0)
941 else if (strcmp(fname,
"loread") == 0)
943 else if (strcmp(fname,
"lowrite") == 0)
950 * Finally check that we got all required large object interface functions
951 * (ones that have been added later than the stone age are instead checked
1012 * Put the structure into the connection control
1020 * converts a 64-bit integer from host byte order to network byte order
1032 /* High order half first, since we're doing MSB-first */
1033 t = (
uint32) (host64 >> 32);
1036 /* Now the low order half */
1045 * converts a 64-bit integer from network byte order to host byte order
#define unconstify(underlying_type, expr)
#define MemSet(start, val, len)
PGresult * PQfn(PGconn *conn, int fnid, int *result_buf, int *result_len, int result_is_int, const PQArgBlock *args, int nargs)
PGresult * PQexec(PGconn *conn, const char *query)
static Oid lo_import_internal(PGconn *conn, const char *filename, Oid oid)
int lo_tell(PGconn *conn, int fd)
static int64_t lo_ntoh64(int64_t net64)
int lo_close(PGconn *conn, int fd)
int lo_truncate64(PGconn *conn, int fd, int64_t len)
static int lo_initialize(PGconn *conn)
Oid lo_creat(PGconn *conn, int mode)
int lo_read(PGconn *conn, int fd, char *buf, size_t len)
int lo_lseek(PGconn *conn, int fd, int offset, int whence)
int lo_open(PGconn *conn, Oid lobjId, int mode)
int64_t lo_lseek64(PGconn *conn, int fd, int64_t offset, int whence)
int64_t lo_tell64(PGconn *conn, int fd)
int lo_write(PGconn *conn, int fd, const char *buf, size_t len)
int lo_truncate(PGconn *conn, int fd, size_t len)
Oid lo_create(PGconn *conn, Oid lobjId)
static int64_t lo_hton64(int64_t host64)
int lo_unlink(PGconn *conn, Oid lobjId)
Oid lo_import(PGconn *conn, const char *filename)
int lo_export(PGconn *conn, Oid lobjId, const char *filename)
Oid lo_import_with_oid(PGconn *conn, const char *filename, Oid lobjId)
if(TABLE==NULL||TABLE_index==NULL)
#define pqClearConnErrorState(conn)
void libpq_append_conn_error(PGconn *conn, const char *fmt,...)
static PgChecksumMode mode
#define PG_STRERROR_R_BUFLEN
static int fd(const char *x, int i)
ExecStatusType resultStatus