00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015 #include "postgres.h"
00016
00017 #include "access/genam.h"
00018 #include "access/heapam.h"
00019 #include "access/htup_details.h"
00020 #include "access/sysattr.h"
00021 #include "catalog/dependency.h"
00022 #include "catalog/indexing.h"
00023 #include "catalog/pg_largeobject.h"
00024 #include "catalog/pg_largeobject_metadata.h"
00025 #include "miscadmin.h"
00026 #include "utils/acl.h"
00027 #include "utils/fmgroids.h"
00028 #include "utils/rel.h"
00029 #include "utils/tqual.h"
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039 Oid
00040 LargeObjectCreate(Oid loid)
00041 {
00042 Relation pg_lo_meta;
00043 HeapTuple ntup;
00044 Oid loid_new;
00045 Datum values[Natts_pg_largeobject_metadata];
00046 bool nulls[Natts_pg_largeobject_metadata];
00047
00048 pg_lo_meta = heap_open(LargeObjectMetadataRelationId,
00049 RowExclusiveLock);
00050
00051
00052
00053
00054 memset(values, 0, sizeof(values));
00055 memset(nulls, false, sizeof(nulls));
00056
00057 values[Anum_pg_largeobject_metadata_lomowner - 1]
00058 = ObjectIdGetDatum(GetUserId());
00059 nulls[Anum_pg_largeobject_metadata_lomacl - 1] = true;
00060
00061 ntup = heap_form_tuple(RelationGetDescr(pg_lo_meta),
00062 values, nulls);
00063 if (OidIsValid(loid))
00064 HeapTupleSetOid(ntup, loid);
00065
00066 loid_new = simple_heap_insert(pg_lo_meta, ntup);
00067 Assert(!OidIsValid(loid) || loid == loid_new);
00068
00069 CatalogUpdateIndexes(pg_lo_meta, ntup);
00070
00071 heap_freetuple(ntup);
00072
00073 heap_close(pg_lo_meta, RowExclusiveLock);
00074
00075 return loid_new;
00076 }
00077
00078
00079
00080
00081
00082 void
00083 LargeObjectDrop(Oid loid)
00084 {
00085 Relation pg_lo_meta;
00086 Relation pg_largeobject;
00087 ScanKeyData skey[1];
00088 SysScanDesc scan;
00089 HeapTuple tuple;
00090
00091 pg_lo_meta = heap_open(LargeObjectMetadataRelationId,
00092 RowExclusiveLock);
00093
00094 pg_largeobject = heap_open(LargeObjectRelationId,
00095 RowExclusiveLock);
00096
00097
00098
00099
00100 ScanKeyInit(&skey[0],
00101 ObjectIdAttributeNumber,
00102 BTEqualStrategyNumber, F_OIDEQ,
00103 ObjectIdGetDatum(loid));
00104
00105 scan = systable_beginscan(pg_lo_meta,
00106 LargeObjectMetadataOidIndexId, true,
00107 SnapshotNow, 1, skey);
00108
00109 tuple = systable_getnext(scan);
00110 if (!HeapTupleIsValid(tuple))
00111 ereport(ERROR,
00112 (errcode(ERRCODE_UNDEFINED_OBJECT),
00113 errmsg("large object %u does not exist", loid)));
00114
00115 simple_heap_delete(pg_lo_meta, &tuple->t_self);
00116
00117 systable_endscan(scan);
00118
00119
00120
00121
00122 ScanKeyInit(&skey[0],
00123 Anum_pg_largeobject_loid,
00124 BTEqualStrategyNumber, F_OIDEQ,
00125 ObjectIdGetDatum(loid));
00126
00127 scan = systable_beginscan(pg_largeobject,
00128 LargeObjectLOidPNIndexId, true,
00129 SnapshotNow, 1, skey);
00130 while (HeapTupleIsValid(tuple = systable_getnext(scan)))
00131 {
00132 simple_heap_delete(pg_largeobject, &tuple->t_self);
00133 }
00134
00135 systable_endscan(scan);
00136
00137 heap_close(pg_largeobject, RowExclusiveLock);
00138
00139 heap_close(pg_lo_meta, RowExclusiveLock);
00140 }
00141
00142
00143
00144
00145
00146
00147
00148
00149
00150
00151
00152
00153
00154 bool
00155 LargeObjectExists(Oid loid)
00156 {
00157 Relation pg_lo_meta;
00158 ScanKeyData skey[1];
00159 SysScanDesc sd;
00160 HeapTuple tuple;
00161 bool retval = false;
00162
00163 ScanKeyInit(&skey[0],
00164 ObjectIdAttributeNumber,
00165 BTEqualStrategyNumber, F_OIDEQ,
00166 ObjectIdGetDatum(loid));
00167
00168 pg_lo_meta = heap_open(LargeObjectMetadataRelationId,
00169 AccessShareLock);
00170
00171 sd = systable_beginscan(pg_lo_meta,
00172 LargeObjectMetadataOidIndexId, true,
00173 SnapshotNow, 1, skey);
00174
00175 tuple = systable_getnext(sd);
00176 if (HeapTupleIsValid(tuple))
00177 retval = true;
00178
00179 systable_endscan(sd);
00180
00181 heap_close(pg_lo_meta, AccessShareLock);
00182
00183 return retval;
00184 }