PostgreSQL在何处处理 sql查询之三

前面已经说过,在 exec_simple_query中,完成sql文的执行。

具体地说,是要构造portal,然后运行 PortalStart , PortalRun...

下面就先看看 portal如何构造:

在 exec_simple_query中,有这么一段:

1         /*
2          * Create unnamed portal to run the query or queries in. If there
3          * already is one, silently drop it.
4          */
5         portal = CreatePortal("", true, true);
6         /* Don't display the portal in pg_cursors */
7         portal->visible = false;

具体的CreatePortal,是如何作的(portalmem.c):

 1 /*
 2  * CreatePortal
 3  *        Returns a new portal given a name.
 4  *
 5  * allowDup: if true, automatically drop any pre-existing portal of the
 6  * same name (if false, an error is raised).
 7  *
 8  * dupSilent: if true, don't even emit a WARNING.
 9  */
10 Portal
11 CreatePortal(const char *name, bool allowDup, bool dupSilent)
12 {
13     Portal        portal;
14 
15     AssertArg(PointerIsValid(name));
16 
17     portal = GetPortalByName(name);
18 
19 
20     if (PortalIsValid(portal))
21     {
22         if (!allowDup)
23             ereport(ERROR,
24                     (errcode(ERRCODE_DUPLICATE_CURSOR),
25                      errmsg("cursor \"%s\" already exists", name)));
26         if (!dupSilent)
27             ereport(WARNING,
28                     (errcode(ERRCODE_DUPLICATE_CURSOR),
29                      errmsg("closing existing cursor \"%s\"",
30                             name)));
31         PortalDrop(portal, false);
32     }
33 
34     /* make new portal structure */
35     portal = (Portal) MemoryContextAllocZero(PortalMemory, sizeof *portal);
36 
37     /* initialize portal heap context; typically it won't store much */
38     portal->heap = AllocSetContextCreate(PortalMemory,
39                                          "PortalHeapMemory",
40                                          ALLOCSET_SMALL_MINSIZE,
41                                          ALLOCSET_SMALL_INITSIZE,
42                                          ALLOCSET_SMALL_MAXSIZE);
43 
44     /* create a resource owner for the portal */
45     portal->resowner = ResourceOwnerCreate(CurTransactionResourceOwner,
46                                            "Portal");
47 
48     /* initialize portal fields that don't start off zero */
49     portal->status = PORTAL_NEW;
50     portal->cleanup = PortalCleanup;
51     portal->createSubid = GetCurrentSubTransactionId();
52     portal->strategy = PORTAL_MULTI_QUERY;
53     portal->cursorOptions = CURSOR_OPT_NO_SCROLL;
54     portal->atStart = true;
55     portal->atEnd = true;        /* disallow fetches until query is set */
56     portal->visible = true;
57     portal->creation_time = GetCurrentStatementStartTimestamp();
58 
59     /* put portal in table (sets portal->name) */
60     PortalHashTableInsert(portal, name);
61 
62     return portal;
63 }

由于调用 CreatePortal 的时候,传递name是空值,所以 portal = GetPortalByName(name); 返回NULL。

通过  MemoryContextAllocZero  建立一个初始的portal,然后再赋予各种值,最后压入哈希表中。此时name依然为空。

posted @ 2013-05-22 10:30  健哥的数据花园  阅读(523)  评论(0编辑  收藏  举报