Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commita51ec45

Browse files
committed
Remove fastpath.c's lame attempt at caching function lookup info across
calls. This has never actually cached anything, because postgres.c doeseach fastpath call as a separate transaction command, and so fastpath.cwould always decide that its cache was outdated. If it had worked, itwould now be failing for calls of oldstyle functions due to danglingpointers in the FmgrInfo struct. Rip it out for simplicity and bug-proofing.
1 parentcfd1843 commita51ec45

File tree

2 files changed

+31
-111
lines changed

2 files changed

+31
-111
lines changed

‎src/backend/tcop/fastpath.c

Lines changed: 30 additions & 97 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
*
99
*
1010
* IDENTIFICATION
11-
* $Header: /cvsroot/pgsql/src/backend/tcop/fastpath.c,v 1.48 2001/03/22 06:16:17 momjian Exp $
11+
* $Header: /cvsroot/pgsql/src/backend/tcop/fastpath.c,v 1.49 2001/06/01 15:45:42 tgl Exp $
1212
*
1313
* NOTES
1414
* This cruft is the server side of PQfn.
@@ -58,15 +58,14 @@
5858
*
5959
*-------------------------------------------------------------------------
6060
*/
61-
6261
#include"postgres.h"
6362

6463
#include"access/xact.h"
6564
#include"catalog/pg_proc.h"
66-
#include"catalog/pg_type.h"
6765
#include"libpq/libpq.h"
6866
#include"libpq/pqformat.h"
6967
#include"tcop/fastpath.h"
68+
#include"utils/lsyscache.h"
7069
#include"utils/syscache.h"
7170

7271

@@ -114,78 +113,38 @@ SendFunctionResult(Datum retval,/* actual return value */
114113
}
115114

116115
/*
117-
* This structure saves enough state so that one can avoid having to
118-
* do catalog lookups over and over again.(Each RPC can require up
119-
* to FUNC_MAX_ARGS+2 lookups, which is quite tedious.)
120-
*
121-
* The previous incarnation of this code just assumed that any argument
122-
* of size <= 4 was by value; this is not correct.There is no cheap
123-
* way to determine function argument length etc.; one must simply pay
124-
* the price of catalog lookups.
116+
* Formerly, this code attempted to cache the function and type info
117+
* looked up by fetch_fp_info, but only for the duration of a single
118+
* transaction command (since in theory the info could change between
119+
* commands). This was utterly useless, because postgres.c executes
120+
* each fastpath call as a separate transaction command, and so the
121+
* cached data could never actually have been reused. If it had worked
122+
* as intended, it would have had problems anyway with dangling references
123+
* in the FmgrInfo struct. So, forget about caching and just repeat the
124+
* syscache fetches on each usage. They're not *that* expensive.
125125
*/
126126
structfp_info
127127
{
128128
Oidfuncid;
129129
FmgrInfoflinfo;/* function lookup info for funcid */
130+
int16arglen[FUNC_MAX_ARGS];
130131
boolargbyval[FUNC_MAX_ARGS];
131-
int32arglen[FUNC_MAX_ARGS];/* signed (for varlena) */
132+
int16retlen;
132133
boolretbyval;
133-
int32retlen;/* signed (for varlena) */
134-
TransactionIdxid;/* when the lookup was done */
135-
CommandIdcid;
136134
};
137135

138136
/*
139-
* We implement one-back caching here.If we need to do more, we can.
140-
* Most routines in tight loops (like PQfswrite -> F_LOWRITE) will do
141-
* the same thing repeatedly.
142-
*/
143-
staticstructfp_infolast_fp= {InvalidOid};
144-
145-
/*
146-
* valid_fp_info
147-
*
148-
* RETURNS:
149-
*T if the state in 'fip' is valid for the given func OID
150-
*F otherwise
151-
*
152-
* "invalid" means:
153-
* The saved state was either uninitialized, for another function,
154-
* or from a previous command.(Commands can do updates, which
155-
* may invalidate catalog entries for subsequent commands.This
156-
* is overly pessimistic but since there is no smarter invalidation
157-
* scheme...).
158-
*/
159-
staticbool
160-
valid_fp_info(Oidfunc_id,structfp_info*fip)
161-
{
162-
Assert(OidIsValid(func_id));
163-
Assert(fip!= (structfp_info*)NULL);
164-
165-
return (OidIsValid(fip->funcid)&&
166-
func_id==fip->funcid&&
167-
TransactionIdIsCurrentTransactionId(fip->xid)&&
168-
CommandIdIsCurrentCommandId(fip->cid));
169-
}
170-
171-
/*
172-
* update_fp_info
137+
* fetch_fp_info
173138
*
174139
* Performs catalog lookups to load a struct fp_info 'fip' for the
175140
* function 'func_id'.
176-
*
177-
* RETURNS:
178-
*The correct information in 'fip'. Sets 'fip->funcid' to
179-
*InvalidOid if an exception occurs.
180141
*/
181142
staticvoid
182-
update_fp_info(Oidfunc_id,structfp_info*fip)
143+
fetch_fp_info(Oidfunc_id,structfp_info*fip)
183144
{
184145
Oid*argtypes;/* an oidvector */
185146
Oidrettype;
186-
HeapTuplefunc_htp,
187-
type_htp;
188-
Form_pg_typetp;
147+
HeapTuplefunc_htp;
189148
Form_pg_procpp;
190149
inti;
191150

@@ -197,56 +156,32 @@ update_fp_info(Oid func_id, struct fp_info * fip)
197156
* funcid is OK, we clear the funcid here.It must not be set to the
198157
* correct value until we are about to return with a good struct
199158
* fp_info, since we can be interrupted (i.e., with an elog(ERROR,
200-
* ...)) at any time.
159+
* ...)) at any time. [No longer really an issue since we don't save
160+
* the struct fp_info across transactions anymore, but keep it anyway.]
201161
*/
202-
MemSet((char*)fip,0,(int)sizeof(structfp_info));
162+
MemSet((char*)fip,0,sizeof(structfp_info));
203163
fip->funcid=InvalidOid;
204164

165+
fmgr_info(func_id,&fip->flinfo);
166+
205167
func_htp=SearchSysCache(PROCOID,
206168
ObjectIdGetDatum(func_id),
207169
0,0,0);
208170
if (!HeapTupleIsValid(func_htp))
209-
elog(ERROR,"update_fp_info: cache lookup for function %u failed",
171+
elog(ERROR,"fetch_fp_info: cache lookup for function %u failed",
210172
func_id);
211173
pp= (Form_pg_proc)GETSTRUCT(func_htp);
212174
rettype=pp->prorettype;
213175
argtypes=pp->proargtypes;
214176

215-
fmgr_info(func_id,&fip->flinfo);
216-
217-
for (i=0;i<fip->flinfo.fn_nargs;++i)
177+
for (i=0;i<pp->pronargs;++i)
218178
{
219179
if (OidIsValid(argtypes[i]))
220-
{
221-
type_htp=SearchSysCache(TYPEOID,
222-
ObjectIdGetDatum(argtypes[i]),
223-
0,0,0);
224-
if (!HeapTupleIsValid(type_htp))
225-
elog(ERROR,"update_fp_info: bad argument type %u for %u",
226-
argtypes[i],func_id);
227-
tp= (Form_pg_type)GETSTRUCT(type_htp);
228-
fip->argbyval[i]=tp->typbyval;
229-
fip->arglen[i]=tp->typlen;
230-
ReleaseSysCache(type_htp);
231-
}/* else it had better be VAR_LENGTH_ARG */
180+
get_typlenbyval(argtypes[i],&fip->arglen[i],&fip->argbyval[i]);
232181
}
233182

234183
if (OidIsValid(rettype))
235-
{
236-
type_htp=SearchSysCache(TYPEOID,
237-
ObjectIdGetDatum(rettype),
238-
0,0,0);
239-
if (!HeapTupleIsValid(type_htp))
240-
elog(ERROR,"update_fp_info: bad return type %u for %u",
241-
rettype,func_id);
242-
tp= (Form_pg_type)GETSTRUCT(type_htp);
243-
fip->retbyval=tp->typbyval;
244-
fip->retlen=tp->typlen;
245-
ReleaseSysCache(type_htp);
246-
}/* else it had better by VAR_LENGTH_RESULT */
247-
248-
fip->xid=GetCurrentTransactionId();
249-
fip->cid=GetCurrentCommandId();
184+
get_typlenbyval(rettype,&fip->retlen,&fip->retbyval);
250185

251186
ReleaseSysCache(func_htp);
252187

@@ -286,6 +221,7 @@ HandleFunctionRequest(void)
286221
Datumretval;
287222
inti;
288223
char*p;
224+
structfp_infomy_fp;
289225
structfp_info*fip;
290226

291227
/*
@@ -324,14 +260,11 @@ HandleFunctionRequest(void)
324260
returnEOF;
325261

326262
/*
327-
* This is where the one-back caching is done. If you want to save
328-
* more state, make this a loop around an array. Given the relatively
329-
* short lifespan of the cache, not clear that there's any win
330-
* possible.
263+
* There used to be a lame attempt at caching lookup info here.
264+
* Now we just do the lookups on every call.
331265
*/
332-
fip=&last_fp;
333-
if (!valid_fp_info(fid,fip))
334-
update_fp_info(fid,fip);
266+
fip=&my_fp;
267+
fetch_fp_info(fid,fip);
335268

336269
if (fip->flinfo.fn_nargs!=nargs||nargs>FUNC_MAX_ARGS)
337270
{

‎src/include/tcop/fastpath.h

Lines changed: 1 addition & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -3,29 +3,16 @@
33
* fastpath.h
44
*
55
*
6-
*
76
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
87
* Portions Copyright (c) 1994, Regents of the University of California
98
*
10-
* $Id: fastpath.h,v 1.8 2001/01/24 19:43:28 momjian Exp $
11-
*
12-
* NOTES
13-
* This information pulled out of tcop/fastpath.c and put
14-
* here so that the PQfn() in be-pqexec.c could access it.
15-
*-cim 2/26/91
9+
* $Id: fastpath.h,v 1.9 2001/06/01 15:45:42 tgl Exp $
1610
*
1711
*-------------------------------------------------------------------------
1812
*/
1913
#ifndefFASTPATH_H
2014
#defineFASTPATH_H
2115

22-
/* ----------------
23-
*fastpath #defines
24-
* ----------------
25-
*/
26-
#defineVAR_LENGTH_RESULT(-1)
27-
#defineVAR_LENGTH_ARG(-5)
28-
2916
externintHandleFunctionRequest(void);
3017

3118
#endif/* FASTPATH_H */

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp