Skip to content

Support package#714

Merged
gaoxueyu merged 20 commits intoIvorySQL:masterfrom
bigplaice:support_package_dev_catchup_master
Dec 6, 2024
Merged

Support package#714
gaoxueyu merged 20 commits intoIvorySQL:masterfrom
bigplaice:support_package_dev_catchup_master

Conversation

@bigplaice
Copy link
Copy Markdown
Collaborator

@bigplaice bigplaice commented Dec 6, 2024

Summary by CodeRabbit

  • New Features

    • Introduced PL/SQL package management, including creation, alteration, and description of packages and package bodies.
    • Added support for package-related commands in the PostgreSQL interactive terminal (psql) with the new \k command.
    • Enhanced privilege management for packages with new ACL functions.
    • Implemented package caching for improved performance.
  • Bug Fixes

    • Improved function return type handling to ensure accuracy in package contexts.
  • Documentation

    • Updated documentation to reflect new package functionalities and commands.
  • Tests

    • Added tests for new package functionalities to ensure robustness and reliability.

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai bot commented Dec 6, 2024

Walkthrough

The changes in this pull request introduce comprehensive support for PL/SQL packages in PostgreSQL. Key additions include new data structures, functions, and command handling for creating, altering, and managing packages and their bodies. The modifications extend to various components, including the SQL parser, access control, caching mechanisms, and the command-line interface. Enhancements to existing functions ensure compatibility with package types, improving the overall functionality and flexibility of the PostgreSQL system regarding package management.

Changes

File Path Change Summary
configure.ac Added a configuration option for enabling explicit cursor unname functionality with --enable-cursor-uname.
contrib/ivorysql_ora/src/sysview/sysview--1.0.sql Introduced functions and views related to database procedures and sequences, including SYS.ORA_CASE_TRANS, SYS.DBA_PROCEDURES, and SYS.DBA_SEQUENCES. Added grants for public access to these views.
contrib/postgres_fdw/sql/ivy_postgres_fdw.sql Modified SQL script to create foreign servers, user mappings, and foreign tables, along with data manipulation operations and triggers.
src/backend/access/common/session.c Integrated dynamic shared memory area (DSA) management into session handling. Updated GetSessionDsmHandle and AttachSession functions.
src/backend/access/hash/hashvalidate.c Enhanced check_hash_func_signature to validate function signatures more robustly by checking return type and argument count.
src/backend/access/index/amvalidate.c Updated check_amproc_signature to improve return type validation using get_func_real_rettype.
src/backend/catalog/aclchk.c Added support for package-related access control functionalities, including ExecGrant_Package and pg_package_aclcheck.
src/backend/catalog/dependency.c Enhanced dependency management to accommodate package objects, including updates to the doDeletion function.
src/backend/catalog/namespace.c Added functions for retrieving package OIDs and checking package visibility.
src/backend/catalog/objectaddress.c Extended object address handling to include packages and package bodies.
src/backend/catalog/pg_aggregate.c Modified AggregateCreate to accommodate new parameters for aggregate functions.
src/backend/catalog/pg_proc.c Enhanced ProcedureCreate function to manage new parameters for return and parameter types.
src/backend/commands/Makefile Added packagecmds.o to the list of object files for compilation.
src/backend/commands/aggregatecmds.c Updated DefineAggregate to handle new parameters for aggregate definitions.
src/backend/commands/alter.c Introduced package handling in various alter commands, including renaming and schema alterations.
src/backend/commands/discard.c Added support for DISCARD_PACKAGES to reset package caches.
src/backend/commands/dropcmds.c Enhanced does_not_exist_skipping to handle package and package body checks.
src/backend/commands/event_trigger.c Updated event trigger functions to recognize package and package body types.
src/backend/commands/functioncmds.c Enhanced function handling to support package types in parameter and return type management.
src/backend/commands/meson.build Added packagecmds.c to the backend sources list.
src/backend/commands/opclasscmds.c Updated assignProcTypes to improve return type validation using get_func_real_rettype.
src/backend/commands/packagecmds.c Implemented functionality for managing PL/SQL packages, including creation, alteration, and dropping of packages and their bodies.
src/backend/commands/seclabel.c Added package and package body support to the SecLabelSupportsObjectType function.
src/backend/commands/typecmds.c Enhanced type and domain management functions to support new parameters for constructors.
src/backend/nodes/makefuncs.c Updated FuncExpr structure to include new fields for package-related metadata.
src/backend/nodes/nodeFuncs.c Enhanced exprType to handle package-related information for FuncExpr nodes.
src/backend/optimizer/plan/setrefs.c Added functionality to manage dependencies for internal functions and packages.
src/backend/optimizer/util/clauses.c Enhanced function expression handling to include package-related checks.
src/backend/oracle_parser/liboracle_parser.c Enhanced Oracle SQL parser to handle PL/SQL packages and package bodies.
src/backend/oracle_parser/ora_gramparse.h Added new enumerations for package body styles in the Oracle parser.
src/backend/parser/Makefile Added parse_package.o to the list of object files for compilation.
src/backend/parser/meson.build Added parse_package.c to the backend sources list.
src/backend/parser/parse_func.c Enhanced function call handling to support package functions.
src/backend/parser/parse_package.c Introduced parsing functionality for PL/SQL packages, including resolution of package names and retrieval of package components.
src/backend/parser/parse_type.c Enhanced type name handling to include package type checks.
src/backend/tcop/fastpath.c Updated fetch_fp_info to enhance retrieval of function metadata.
src/backend/tcop/utility.c Added support for package-related commands in utility command processing.
src/backend/utils/adt/acl.c Introduced has_package_privilege_id to check user privileges on packages.
src/backend/utils/adt/regproc.c Enhanced procedure and operator name handling to include package information.
src/backend/utils/cache/Makefile Added packagecache.o to the list of object files in the cache utilities.
src/backend/utils/cache/lsyscache.c Introduced functions to handle real argument and return types in the context of Oracle compatibility.
src/backend/utils/cache/packagecache.c Implemented caching mechanisms for PL/SQL packages, including insertion, lookup, and validation functions.
src/backend/utils/cache/plancache.c Added functions to manage plan cache invalidation for packages.
src/backend/utils/fmgr/funcapi.c Enhanced handling of polymorphic types and internal function calls related to packages.
src/bin/pg_dump/common.c Extended schema data handling to include user-defined packages.
src/bin/pg_dump/dumputils.c Expanded privilege parsing to include packages.
src/bin/pg_dump/pg_backup_archiver.c Updated object description handling to include packages.
src/bin/pg_dump/pg_dump.h Added new enumeration and structure definitions for package management in the dump utility.
src/bin/pg_dump/pg_dump_sort.c Introduced priority handling for packages in the dump process.
src/bin/psql/command.c Added support for the \k command to describe packages in the interactive terminal.
src/bin/psql/describe.c Implemented describePackages function for package descriptions.
src/bin/psql/describe.h Declared describePackages function for package management.
src/bin/psql/tab-complete.c Enhanced tab completion to include package-related commands.
src/include/catalog/Makefile Updated catalog header processing to include pg_package.h and pg_package_body.h.
src/include/catalog/meson.build Added pg_package.h and pg_package_body.h to the catalog headers list.
src/include/catalog/namespace.h Added function declarations for package management.
src/include/catalog/pg_attribute.h Adjusted field positioning in the pg_attribute structure without altering functionality.
src/include/catalog/pg_default_acl.h Added macro for default ACL object type for packages.
src/include/catalog/pg_package.h Defined the schema for the pg_package catalog, including relevant fields and indexes.
src/include/catalog/pg_package_body.h Defined the schema for the pg_package_body catalog, including relevant fields and indexes.
src/include/catalog/pg_proc.h Enhanced procedure catalog to include return type and parameter type name handling.
src/include/commands/defrem.h Updated interpret_function_parameter_list to include new parameters for type names.
src/include/commands/packagecmds.h Added function declarations for package management operations.
src/include/executor/execExpr.h Added field for package OID in the ExprEvalStep structure.
src/include/funcapi.h Expanded the PLiSQL_funcs_call struct to include function pointers for package management.
src/include/nodes/parsenodes.h Introduced structures and enumerations for package management in the parser.
src/include/nodes/primnodes.h Updated FuncExpr structure to include new fields for package metadata.
src/include/oracle_parser/ora_kwlist.h Added new keywords related to packages in the Oracle parser.
src/include/parser/parse_package.h Defined structures and functions for managing packages in the parser.
src/include/parser/parse_type.h Added function declaration for quoting type names.
src/include/tcop/cmdtaglist.h Introduced new command tags for package management operations.
src/include/utils/acl.h Added functions and macros for package ACL management.
src/include/utils/lsyscache.h Introduced functions for retrieving real argument and return types.
src/include/utils/packagecache.h Defined structures and functions for managing a package cache.
src/include/utils/plancache.h Added function declaration for package cache invalidation.
src/oracle_fe_utils/ora_psqlscan.l Updated the lexer to recognize the "package" keyword in Oracle SQL.
src/oracle_test/modules/plsample/plsample.c Enhanced return type handling in the plsample_func_handler function.

Poem

In the garden of code, where packages bloom,
New features sprout, dispelling the gloom.
With functions and views, our work is complete,
PostgreSQL packages, a marvelous feat!
So hop with delight, let the changes unfold,
A tale of enhancements, in stories retold! 🐇✨


Thank you for using CodeRabbit. We offer it for free to the OSS community and would appreciate your support in helping us grow. If you find it useful, would you consider giving us a shout-out on your favorite social media?

❤️ Share
🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Generate unit testing code for this file.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query. Examples:
    • @coderabbitai generate unit testing code for this file.
    • @coderabbitai modularize this function.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read src/utils.ts and generate unit testing code.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.
    • @coderabbitai help me debug CodeRabbit configuration file.

Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments.

CodeRabbit Commands (Invoked using PR comments)

  • @coderabbitai pause to pause the reviews on a PR.
  • @coderabbitai resume to resume the paused reviews.
  • @coderabbitai review to trigger an incremental review. This is useful when automatic reviews are disabled for the repository.
  • @coderabbitai full review to do a full review from scratch and review all the files again.
  • @coderabbitai summary to regenerate the summary of the PR.
  • @coderabbitai resolve resolve all the CodeRabbit review comments.
  • @coderabbitai configuration to show the current CodeRabbit configuration for the repository.
  • @coderabbitai help to get help.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

CodeRabbit Configuration File (.coderabbit.yaml)

  • You can programmatically configure CodeRabbit by adding a .coderabbit.yaml file to the root of your repository.
  • Please see the configuration documentation for more information.
  • If your editor has YAML language server enabled, you can add the path at the top of this file to enable auto-completion and validation: # yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json

Documentation and Community

  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

@bigplaice bigplaice changed the title Support package dev catchup master Support package Dec 6, 2024
@bigplaice bigplaice closed this Dec 6, 2024
Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 22

🧹 Outside diff range and nitpick comments (58)
src/bin/pg_dump/pg_dump.c (2)

12280-12283: Consider making Oracle compatibility mode more explicit

The Oracle compatibility mode check is implicit:

if (((ArchiveHandle *) fout)->format == archNull &&
    db_mode == DB_ORACLE)

Consider extracting this check into a helper function for better readability:

+ static bool isOracleCompatMode(Archive *fout)
+ {
+     return ((ArchiveHandle *)fout)->format == archNull && db_mode == DB_ORACLE;
+ }

- if (((ArchiveHandle *) fout)->format == archNull &&
-     db_mode == DB_ORACLE)
+ if (isOracleCompatMode(fout))

Line range hint 247-18745: Consider architectural improvements for package support

The implementation successfully adds PL/SQL package support, but consider the following architectural improvements:

  1. Create a dedicated error handling module for consistent error management across package-related operations
  2. Abstract Oracle compatibility mode into a separate module to improve maintainability
  3. Implement a memory management strategy that ensures proper cleanup in all error paths
  4. Consider adding integration tests specifically for package dumping scenarios

Would you like help implementing any of these architectural improvements?

src/backend/oracle_parser/ora_gram.y (2)

7184-7203: Consider additional privilege checks for package operations

While the grammar correctly integrates package operations with existing statements, ensure that appropriate privilege checks are implemented in the execution phase for:

  • Package creation/dropping
  • Package ownership transfers
  • Schema changes

Also applies to: 7458-7465, 10385-10393, 11101-11109, 11413-11420


9977-10070: Add grammar documentation for package support

Consider adding documentation comments above the package-related grammar rules to:

  1. Explain the package creation syntax
  2. Document the relationship between package specifications and bodies
  3. Provide examples of valid package declarations
src/include/catalog/pg_package_body.h (1)

3-3: Add space after 'File:' in the header comment

In line 3, there's a missing space after File:. For consistency with other header comments, please add a space.

Apply this diff:

- * File:pg_package_body.h
+ * File: pg_package_body.h
src/include/catalog/pg_package.h (2)

3-3: Add space after 'File:' in the header comment

In line 3, add a space after File: for consistency.

Apply this diff:

- * File:pg_package.h
+ * File: pg_package.h

35-35: Default namespace should use standard macros

In line 35, for pkgnamespace, consider using BKI_DEFAULT(PG_CATALOG_NAMESPACE) instead of hardcoding pg_catalog.

Apply this diff:

- Oid            pkgnamespace BKI_DEFAULT(pg_catalog) BKI_LOOKUP(pg_namespace);
+ Oid            pkgnamespace BKI_DEFAULT(PG_CATALOG_NAMESPACE) BKI_LOOKUP(pg_namespace);

This ensures consistency and proper linkage to the predefined namespace.

src/include/parser/parse_package.h (2)

3-3: Add space after 'File:' in the header comment

In line 3, add a space after File: for consistency.

Apply this diff:

- * File:parse_package.h
+ * File: parse_package.h

44-55: Clarify the purpose of 'PkgEntry' and 'PkgEntryType'

The PkgEntryType enum and PkgEntry struct should have clear documentation explaining their roles in package parsing.

Consider adding comments to explain:

  • The different values of PkgEntryType and when they are used.
  • The relationship between PkgEntry, PkgType, and PkgVar.
src/include/utils/packagecache.h (3)

3-3: Add space after 'File:' in the header comment

In line 3, add a space after File: for consistency.

Apply this diff:

- * File:packagecache.h
+ * File: packagecache.h

27-32: Fix typos and improve comments for clarity

There are typos and grammatical errors in the comments explaining PackageCacheStatus. Improve the comments for better understanding.

Apply this diff:

- * at fast, if package cache status hasn't bee update,
- * we don't compile package and body tid and xid
+ * Initially, if the package cache status hasn't been updated,
+ * we don't compile the package and body TID and XID.

And correct 'bee' to 'been', 'wether' to 'whether', 'intable' to 'in table', etc.


82-88: Clarify the purpose of 'package_parse_flags' enum

Add documentation to explain the different flags in package_parse_flags and their usage.

Consider adding comments for each enum value to describe when it should be used.

src/backend/access/common/session.c (2)

Line range hint 70-74: Handle possible memory allocation failure

In the function GetSessionDsmHandle, after attempting to create the DSM segment, check for allocation failure before proceeding.

Apply this diff to handle the error case:

     seg = dsm_create(size, DSM_CREATE_NULL_IF_MAXSEGMENTS);
+    if (seg == NULL)
+    {
+        MemoryContextSwitchTo(old_context);
+        return DSM_HANDLE_INVALID;
+    }

This ensures that the function gracefully handles the failure to create a DSM segment.


Line range hint 109-116: Consider race conditions during session attachment

In AttachSession, ensure thread safety when multiple workers attempt to attach to the session.

Consider adding synchronization mechanisms if necessary to handle concurrent access during session attachment.

src/backend/parser/parse_package.c (4)

95-96: Redundant break Statement After default Case

The break; statement after the default: label is unnecessary since it's the last statement in the switch block.

Remove the redundant break; statement:

         default:
             break;
     }
-
-    break;

123-144: Use Case-Insensitive Comparison for Database Name

When comparing first_name with the current database name, it's safer to use a case-insensitive comparison to prevent mismatches due to case differences.

Use pg_strcasecmp for comparison:

-    if (strcmp(first_name, get_database_name(MyDatabaseId)) == 0)
+    if (pg_strcasecmp(first_name, get_database_name(MyDatabaseId)) == 0)

383-392: Avoid Multiple Initializations of plisql_internal_funcs

The function plisql_internel_funcs_init is called multiple times, which may be unnecessary and could impact performance.

Consider initializing plisql_internal_funcs once during startup or caching the initialized state to prevent redundant initializations.


Line range hint 445-496: Memory Leak in set_pkgtype_from_funcexpr Function

In the set_pkgtype_from_funcexpr function, the allocated memory for func_name and chema_name is not freed, leading to a memory leak.

Free the allocated memory before the function returns:

     pfree(funcexpr);
     pfree(func_name);
     pfree(pstate);
     pfree(funcexpr);
+    pfree(chema_name);
src/include/funcapi.h (1)

173-197: Add Documentation for New Function Pointers in PLiSQL_funcs_call

The newly added function pointers in the PLiSQL_funcs_call struct lack documentation. This makes it harder for other developers to understand their purpose and usage.

Please add comments for each new function pointer to explain their functionality and expected parameters.

src/backend/utils/cache/packagecache.c (1)

310-316: Optimize Cache Invalidation Logic

The current cache invalidation logic may not be optimal in terms of performance. Comparing hash values can be inefficient.

Consider using direct OID comparisons or other efficient methods for cache invalidation to improve performance.

src/backend/parser/parse_type.c (1)

497-546: Code Duplication in Type Name Buffer Functions

The new function appendQuoteTypeNameToBuffer shares similar logic with appendTypeNameToBuffer, leading to code duplication.

Refactor the common code into a shared helper function to adhere to the DRY (Don't Repeat Yourself) principle.

src/backend/commands/alter.c (1)

Line range hint 886-891: Update Ownership Dependencies When Changing Package Owner

In ExecAlterOwnerStmt, when changing the owner of a package, it's important to update the ownership dependencies for all objects contained within the package.

Verify that ownership changes cascade appropriately to all dependent objects within the package.

src/backend/oracle_parser/liboracle_parser.c (1)

566-671: Consider Refactoring Nested Conditions for Readability

The deeply nested conditional statements within this block handling OraBody_PACKAGE and OraBody_PACKAGEBODY can be refactored to improve readability and maintainability. Simplifying the nested if and while structures will make the code easier to understand and reduce potential errors.

src/backend/catalog/pg_proc.c (1)

Line range hint 83-84: Typographical Correction in Error Message

The error message "doesn't recognise object type" contains a typographical error. It should be "doesn't recognize object type" to maintain consistency with standard English spelling used in the codebase.

Apply this diff to correct the typo:

-        errcode(ERRCODE_WRONG_OBJECT_TYPE),
-         errmsg("cannot change routine kind"),
-         (oldproc->prokind == PROKIND_AGGREGATE ?
-          errdetail("\"%s\" is an aggregate function.", procedureName) :
-          oldproc->prokind == PROKIND_FUNCTION ?
-          errdetail("\"%s\" is a function.", procedureName) :
-          oldproc->prokind == PROKIND_PROCEDURE ?
-          errdetail("\"%s\" is a procedure.", procedureName) :
-          oldproc->prokind == PROKIND_WINDOW ?
-          errdetail("\"%s\" is a window function.", procedureName) :
-          0)));
+        errcode(ERRCODE_WRONG_OBJECT_TYPE),
+         errmsg("cannot change routine kind"),
+         (oldproc->prokind == PROKIND_AGGREGATE ?
+          errdetail("\"%s\" is an aggregate function.", procedureName) :
+          oldproc->prokind == PROKIND_FUNCTION ?
+          errdetail("\"%s\" is a function.", procedureName) :
+          oldproc->prokind == PROKIND_PROCEDURE ?
+          errdetail("\"%s\" is a procedure.", procedureName) :
+          oldproc->prokind == PROKIND_WINDOW ?
+          errdetail("\"%s\" is a window function.", procedureName) :
+          0)));
src/backend/commands/packagecmds.c (2)

83-84: Typo in Error Message: Correct 'proper' to 'property'

The error message "invalid package proper" contains a typo. It should be "invalid package property" for clarity and correctness.

Apply this diff to correct the typo:

-				elog(ERROR, "invalid package proper");
+				elog(ERROR, "invalid package property");

735-736: Typographical Correction in Error Message

The error message "doesn't recognise alter flag" contains a typographical error. It should be "doesn't recognize alter flag" to maintain consistency with standard English spelling used in the codebase.

Apply this diff to correct the typo:

-			elog(ERROR, "doesn't recognise alter flag:%d", stmt->alter_flag);
+			elog(ERROR, "doesn't recognize alter flag:%d", stmt->alter_flag);
src/backend/utils/adt/regproc.c (2)

Line range hint 344-382: Ensure Safe Access to p_argtypeNames Array

When accessing p_argtypeNames[i], ensure that the array is properly allocated and that the index i does not exceed the array bounds to prevent potential buffer overruns or segmentation faults.

Apply this diff to add bounds checking:

 for (i = 0; i < nargs; i++)
 {
     Oid         thisargtype = procform->proargtypes.values[i];

+    if (p_argtypeNames != NULL && i < nargs && strcmp(p_argtypeNames[i], "") != 0)
     {
         TypeName *tname = stringToNode(p_argtypeNames[i]);

         appendStringInfoString(&buf,
                                (flags & FORMAT_PROC_FORCE_QUALIFY) != 0 ?
                                TypeNameToQuoteString(tname):
                                TypeNameToString(tname));
         pfree(tname);
     }
     else
         appendStringInfoString(&buf,
                                (flags & FORMAT_PROC_FORCE_QUALIFY) != 0 ?
                                format_type_be_qualified(thisargtype) :
                                format_type_be(thisargtype));
 }

Line range hint 425-456: Update Function Documentation for Modified Signature

The function format_procedure_parts has an updated signature to include p_argtypeNames. Ensure that the function's documentation and comments are updated accordingly to reflect this change, aiding future maintainability.

src/backend/utils/fmgr/funcapi.c (1)

47-47: Initialize All Fields in plisql_internal_funcs Structure

The plisql_internal_funcs structure is initialized with multiple NULL entries. Verify that all fields of the structure are correctly initialized, and consider using designated initializers for clarity.

Apply this diff to improve initialization clarity:

PLiSQL_funcs_call plisql_internal_funcs = {
    .get_internal_func_result_tupdesc = NULL,
    .get_internal_func_name = NULL,
    .get_internal_func_result_type = NULL,
    .get_internal_func_outargs = NULL,
    .get_inernal_func_result_name = NULL,
    .initialized = false
    /* Initialize remaining fields as necessary */
};
src/backend/catalog/namespace.c (1)

951-954: Update comments to refer to 'package' instead of 'relation'

The comments within PackageIsVisible still refer to 'relation' instead of 'package', which may cause confusion.

Apply this diff to correct the comments:

     /*
-     * If it is in the path, it might still not be visible; it could be
-     * hidden by another relation of the same name earlier in the path. So
-     * we must do a slow check for conflicting relations.
+     * If it is in the path, it might still not be visible; it could be
+     * hidden by another package of the same name earlier in the path. So
+     * we must do a slow check for conflicting packages.
      */
src/include/nodes/parsenodes.h (4)

4307-4307: Correct typographical errors in the comment for propers.

The comment for propers contains typographical errors: "invok rigth" should be "invoke right".

Apply this diff to fix the typos:

-    	List		*propers;		/* invok rigth or access by or default collation */
+    	List		*propers;		/* invoke right or access by or default collation */

4309-4309: Clarify the comment for the editable field.

The comment 'EDITIONABLE' may not accurately describe the purpose of the editable field. Consider updating the comment for clarity and consistency with the field name.

Apply this diff to improve the comment:

-    	bool		editable;		/* EDITIONABLE */
+    	bool		editable;		/* Is the package editable? */

4316-4316: Add missing comment for the replace field in CreatePackageBodyStmt.

The replace field lacks a comment explaining its purpose, which may reduce code readability.

Apply this diff to add the missing comment:

-    	bool		replace;
+    	bool		replace;		/* T => replace if already exists */

4334-4338: Ensure consistent alignment and indentation in AlterPackageStmt struct.

The member declarations in AlterPackageStmt have inconsistent alignment, which can affect readability.

Apply this diff to align the struct members:

    	typedef struct AlterPackageStmt
    	{
-    		NodeTag					type;
-    		List					*pkgname;
-    		package_alter_flag		alter_flag;
-    		bool					editable;
-    		List					*parameters;
+    		NodeTag				type;
+    		List				*pkgname;
+    		package_alter_flag	alter_flag;
+    		bool				editable;
+    		List				*parameters;
    	} AlterPackageStmt;
src/backend/catalog/aclchk.c (1)

2325-2327: Initialize arrays with proper size using pg_pipeline functions.

Consider using memset instead of MemSet for standard C compliance, or ensure that MemSet is correctly defined for these types.

Apply this diff if appropriate:

-    		MemSet(values, 0, sizeof(values));
-    		MemSet(nulls, false, sizeof(nulls));
-    		MemSet(replaces, false, sizeof(replaces));
+    		memset(values, 0, sizeof(values));
+    		memset(nulls, false, sizeof(nulls));
+    		memset(replaces, false, sizeof(replaces));
src/backend/utils/adt/ruleutils.c (3)

Line range hint 3425-3526: Add comments to explain the purpose and behavior of pg_get_package_head().

The new pg_get_package_head() function is added to generate the "CREATE OR REPLACE PACKAGE" statement for a given package OID. However, there are no comments explaining what this function does, what parameters it takes, and what it returns. Adding some header comments would improve the code readability and maintainability.


3455-3460: Consider extracting the AUTHID clause generation into a separate function.

The code to generate the AUTHID clause based on the pkg_form->define_invok flag is mixed with other parts of the function. Extracting this into a separate function like get_package_authid_clause() could improve modularity and readability.


3519-3521: Add a comment explaining the purpose of replacing the last comma.

The code replaces the last comma with a closing parenthesis when generating the ACCESSIBLE BY clause. Add a comment explaining why this is necessary, as it may not be immediately obvious.

src/include/commands/packagecmds.h (3)

1-16: Enhance file documentation with more detailed package management overview

While the header includes basic file information, it would benefit from additional documentation explaining:

  • The relationship between packages and package bodies
  • Key concepts and terminology
  • Usage examples or references to documentation

20-22: Consider adding more essential PostgreSQL headers

The current includes might be insufficient. Consider adding:

  • postgres.h as it's typically required first
  • access/xact.h for transaction management
  • utils/acl.h for permission checking functions

43-46: Improve parameter documentation for get_functup_bytypenames

The function signature is complex with multiple parameters but lacks documentation explaining:

  • Purpose and usage context
  • Parameter requirements and constraints
  • Return value semantics
src/include/catalog/pg_default_acl.h (1)

71-71: Fix typo in comment: "pakcage" should be "package"

The DEFACLOBJ_PACKAGE constant is correctly defined, but there's a typo in the comment.

-#define DEFACLOBJ_PACKAGE		'P' /* pakcage */
+#define DEFACLOBJ_PACKAGE		'P' /* package */
src/include/commands/defrem.h (1)

77-78: Fix typo in parameter name

The parameter name contains a typo: paramtertypeNames should be parameterTypeNames.

-                                         ArrayType **paramtertypeNames);
+                                         ArrayType **parameterTypeNames);
src/include/catalog/pg_proc.h (1)

222-224: Maintain consistent parameter naming style

The parameter naming is inconsistent:

  • parametertypeNames (camelCase)
  • rettypeName (camelCase with different word boundary)

Consider standardizing the naming convention:

-                                   Datum parametertypeNames,
-                                   char *rettypeName);
+                                   Datum parameterTypeNames,
+                                   char *returnTypeName);
src/include/catalog/namespace.h (1)

95-96: LGTM! Consider adding documentation comments.

The new package-related functions follow consistent naming patterns and are well-placed. Consider adding documentation comments to describe their behavior, similar to other functions in this file.

+/* Get package OID for given package name */
 extern Oid PkgnameGetPkgid(const char *pkgname);
+/* Check if package is visible in current search path */
 extern bool PackageIsVisible(Oid pkgoid);
src/include/utils/acl.h (1)

166-166: Consider expanding package ACL rights

Currently, packages only support EXECUTE rights. Consider whether additional rights might be needed for package management, such as ALTER or DEBUG rights.

src/bin/pg_dump/pg_dump_sort.c (1)

1274-1278: Fix formatting in package description string

There's an extra space after "PACKAGE" in the format string.

-					" PACKAGE %s(ID %d OID %u)",
+					"PACKAGE %s  (ID %d OID %u)",
src/oracle_fe_utils/ora_psqlscan.l (1)

1079-1079: LGTM! Consider adding a comment for clarity.

The addition of "package" to the list of identifiers is correct and necessary for PL/SQL package support.

Consider adding a comment to explain that this is for PL/SQL package support:

-						pg_strcasecmp(yytext, "package") == 0 || 
+						pg_strcasecmp(yytext, "package") == 0 ||  /* For PL/SQL package support */
src/backend/commands/event_trigger.c (1)

2232-2235: Consider pluralizing package-related object types for consistency.

While most object types use plural forms in ALTER DEFAULT PRIVILEGES (e.g., "TABLES", "SEQUENCES"), package-related types don't follow this pattern.

Consider using plural forms for consistency:

-			return "PACKAGE";
+			return "PACKAGES";
-			return "PACKAGE BODY";
+			return "PACKAGE BODIES";
configure.ac (1)

153-161: LGTM! Consider adding documentation for the new configuration option.

The implementation of the --enable-cursor-unname configuration option follows good practices and integrates well with the existing build system. However, it would be helpful to add documentation explaining:

  • The purpose and impact of this option
  • When users should consider enabling it
  • Any dependencies or interactions with other features
src/backend/nodes/nodeFuncs.c (1)

77-87: LGTM! Package information handling is well-structured.

The implementation:

  • Properly checks function origin using the FUNC_EXPR_FROM_PACKAGE macro
  • Sets package info only when needed
  • Maintains proper control flow
  • Follows the existing code style

Consider adding error handling for the package info setup functions:

 if (FUNC_EXPR_FROM_PACKAGE(funcexpr->function_from))
-    set_pkginfo_from_funcexpr(funcexpr);
+    if (!set_pkginfo_from_funcexpr(funcexpr))
+        elog(ERROR, "failed to set package info for function expression");
src/backend/utils/adt/acl.c (2)

3488-3519: LGTM: Package privilege checking implementation

The has_package_privilege_id function is well implemented, following the established pattern for privilege checking functions. It properly handles privilege conversion, package existence verification, and ACL checking.

However, consider adding a more specific error message when the package does not exist:

 if (!SearchSysCacheExists1(PKGOID, ObjectIdGetDatum(pakcageoid)))
+    ereport(ERROR,
+           (errcode(ERRCODE_UNDEFINED_OBJECT),
+            errmsg("package with OID %u does not exist", pakcageoid)));

3497-3497: Fix typo in variable name

There's a typo in the variable name "pakcageoid".

-    Oid         pakcageoid = PG_GETARG_OID(0);
+    Oid         packageoid = PG_GETARG_OID(0);

Also applies to: 3498-3498

contrib/postgres_fdw/sql/ivy_postgres_fdw.sql (1)

4110-4111: Consider adding length validation for string concatenation.

The UPDATE operation concatenates column c with itself which could potentially exceed the varchar2(1024) limit. Consider adding a length check or handling potential truncation.

-- Add length validation before concatenation
UPDATE async_pt 
SET c = CASE 
    WHEN LENGTH(c || c) <= 1024 THEN c || c
    ELSE c -- or handle truncation as needed
END 
WHERE b = 0;
src/bin/psql/describe.c (2)

3782-3789: Add function documentation comment.

The function lacks a proper documentation comment describing its purpose, parameters and return value.

Add a documentation comment like this:

+/*
+ * describePackages
+ *
+ * Lists PL/SQL packages in the database.
+ *
+ * pattern: Optional regexp pattern to filter package names
+ * verbose: If true, show additional details like package body
+ * showSystem: If true, include system packages
+ *
+ * Returns true on success, false on failure
+ */

3859-3889: LGTM with minor suggestions.

The query execution and result handling follows the standard pattern used in other similar functions. However, consider these improvements:

  1. Add error message translation:
-pg_log_error("Did not find any package named \"%s\".", pattern);
+pg_log_error(_("Did not find any package named \"%s\"."), pattern);

-pg_log_error("Did not find any packages.");
+pg_log_error(_("Did not find any packages."));
  1. Consider adding a footer with total package count when verbose mode is enabled, similar to other describe functions.
configure (2)

1534-1534: Enhance the help text documentation

The current help text "enable explicit cursor uname" is too terse. Consider providing more details about:

  • The purpose and impact of this feature
  • The default value
  • Any dependencies or requirements

Example improvement:

-  --enable-cursor-unname  enable explicit cursor uname
+  --enable-cursor-unname  enable explicit cursor unnamed support in PL/SQL packages
+                          (default: no)

3195-3220: Clean up excessive blank lines while implementation looks good

The implementation follows the standard autoconf pattern with proper error handling and safe defaults. However, there are excessive blank lines (3218-3220) before the next section.

  else
    enable_cursor_unname=no
  fi

-

-

-

#
# Default port number (--with-pgport), default 5432
#
+
+ #
+ # Default port number (--with-pgport), default 5432
+ #
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL

📥 Commits

Reviewing files that changed from the base of the PR and between cea97fa and a976db2.

⛔ Files ignored due to path filters (10)
  • contrib/postgres_fdw/expected/ivy_postgres_fdw.out is excluded by !**/*.out
  • src/include/catalog/pg_proc.dat is excluded by !**/*.dat
  • src/oracle_test/regress/expected/oidjoins.out is excluded by !**/*.out
  • src/oracle_test/regress/expected/ora_package.out is excluded by !**/*.out
  • src/pl/plisql/src/expected/plisql_call.out is excluded by !**/*.out
  • src/pl/plisql/src/expected/plisql_nested_subproc.out is excluded by !**/*.out
  • src/pl/plisql/src/expected/plisql_nested_subproc2.out is excluded by !**/*.out
  • src/test/regress/expected/oidjoins.out is excluded by !**/*.out
  • src/test/regress/expected/oidjoins_1.out is excluded by !**/*.out
  • src/test/regress/expected/sanity_check_1.out is excluded by !**/*.out
📒 Files selected for processing (82)
  • configure (3 hunks)
  • configure.ac (1 hunks)
  • contrib/ivorysql_ora/src/sysview/sysview--1.0.sql (1 hunks)
  • contrib/postgres_fdw/sql/ivy_postgres_fdw.sql (1 hunks)
  • src/backend/access/common/session.c (1 hunks)
  • src/backend/access/hash/hashvalidate.c (1 hunks)
  • src/backend/access/index/amvalidate.c (2 hunks)
  • src/backend/catalog/aclchk.c (19 hunks)
  • src/backend/catalog/dependency.c (5 hunks)
  • src/backend/catalog/namespace.c (5 hunks)
  • src/backend/catalog/objectaddress.c (9 hunks)
  • src/backend/catalog/pg_aggregate.c (1 hunks)
  • src/backend/catalog/pg_proc.c (7 hunks)
  • src/backend/commands/Makefile (1 hunks)
  • src/backend/commands/aggregatecmds.c (2 hunks)
  • src/backend/commands/alter.c (8 hunks)
  • src/backend/commands/discard.c (3 hunks)
  • src/backend/commands/dropcmds.c (1 hunks)
  • src/backend/commands/event_trigger.c (2 hunks)
  • src/backend/commands/functioncmds.c (16 hunks)
  • src/backend/commands/meson.build (1 hunks)
  • src/backend/commands/opclasscmds.c (8 hunks)
  • src/backend/commands/packagecmds.c (1 hunks)
  • src/backend/commands/seclabel.c (1 hunks)
  • src/backend/commands/typecmds.c (4 hunks)
  • src/backend/nodes/makefuncs.c (1 hunks)
  • src/backend/nodes/nodeFuncs.c (2 hunks)
  • src/backend/optimizer/plan/setrefs.c (4 hunks)
  • src/backend/optimizer/util/clauses.c (14 hunks)
  • src/backend/oracle_parser/liboracle_parser.c (3 hunks)
  • src/backend/oracle_parser/ora_gram.y (24 hunks)
  • src/backend/oracle_parser/ora_gramparse.h (1 hunks)
  • src/backend/parser/Makefile (1 hunks)
  • src/backend/parser/meson.build (1 hunks)
  • src/backend/parser/parse_func.c (5 hunks)
  • src/backend/parser/parse_package.c (1 hunks)
  • src/backend/parser/parse_type.c (3 hunks)
  • src/backend/tcop/fastpath.c (1 hunks)
  • src/backend/tcop/utility.c (8 hunks)
  • src/backend/utils/adt/acl.c (3 hunks)
  • src/backend/utils/adt/regproc.c (5 hunks)
  • src/backend/utils/adt/ruleutils.c (8 hunks)
  • src/backend/utils/cache/Makefile (1 hunks)
  • src/backend/utils/cache/lsyscache.c (3 hunks)
  • src/backend/utils/cache/meson.build (1 hunks)
  • src/backend/utils/cache/packagecache.c (1 hunks)
  • src/backend/utils/cache/plancache.c (3 hunks)
  • src/backend/utils/fmgr/funcapi.c (15 hunks)
  • src/bin/pg_dump/common.c (2 hunks)
  • src/bin/pg_dump/dumputils.c (1 hunks)
  • src/bin/pg_dump/pg_backup_archiver.c (1 hunks)
  • src/bin/pg_dump/pg_dump.c (5 hunks)
  • src/bin/pg_dump/pg_dump.h (3 hunks)
  • src/bin/pg_dump/pg_dump_sort.c (3 hunks)
  • src/bin/psql/command.c (1 hunks)
  • src/bin/psql/describe.c (1 hunks)
  • src/bin/psql/describe.h (1 hunks)
  • src/bin/psql/tab-complete.c (11 hunks)
  • src/include/catalog/Makefile (1 hunks)
  • src/include/catalog/meson.build (1 hunks)
  • src/include/catalog/namespace.h (1 hunks)
  • src/include/catalog/pg_attribute.h (1 hunks)
  • src/include/catalog/pg_default_acl.h (1 hunks)
  • src/include/catalog/pg_package.h (1 hunks)
  • src/include/catalog/pg_package_body.h (1 hunks)
  • src/include/catalog/pg_proc.h (2 hunks)
  • src/include/commands/defrem.h (1 hunks)
  • src/include/commands/packagecmds.h (1 hunks)
  • src/include/executor/execExpr.h (1 hunks)
  • src/include/funcapi.h (4 hunks)
  • src/include/nodes/parsenodes.h (3 hunks)
  • src/include/nodes/primnodes.h (2 hunks)
  • src/include/oracle_parser/ora_kwlist.h (3 hunks)
  • src/include/parser/parse_package.h (1 hunks)
  • src/include/parser/parse_type.h (1 hunks)
  • src/include/tcop/cmdtaglist.h (4 hunks)
  • src/include/utils/acl.h (2 hunks)
  • src/include/utils/lsyscache.h (2 hunks)
  • src/include/utils/packagecache.h (1 hunks)
  • src/include/utils/plancache.h (1 hunks)
  • src/oracle_fe_utils/ora_psqlscan.l (1 hunks)
  • src/oracle_test/modules/plsample/plsample.c (1 hunks)
⛔ Files not processed due to max files limit (15)
  • src/oracle_test/regress/parallel_schedule
  • src/pl/plisql/src/Makefile
  • src/pl/plisql/src/meson.build
  • src/pl/plisql/src/pl_comp.c
  • src/pl/plisql/src/pl_exec.c
  • src/pl/plisql/src/pl_funcs.c
  • src/pl/plisql/src/pl_gram.y
  • src/pl/plisql/src/pl_handler.c
  • src/pl/plisql/src/pl_package.h
  • src/pl/plisql/src/pl_scanner.c
  • src/pl/plisql/src/pl_subproc_function.c
  • src/pl/plisql/src/pl_subproc_function.h
  • src/pl/plisql/src/plisql.h
  • src/pl/plisql/src/sql/plisql_nested_subproc.sql
  • src/pl/plisql/src/sql/plisql_nested_subproc2.sql
🔥 Files not summarized due to errors (3)
  • configure: Error: Server error: no LLM provider could handle the message
  • src/bin/pg_dump/pg_dump.c: Error: Server error: no LLM provider could handle the message
  • src/backend/oracle_parser/ora_gram.y: Error: Server error: no LLM provider could handle the message
✅ Files skipped from review due to trivial changes (1)
  • src/include/catalog/pg_attribute.h
🔇 Additional comments (135)
src/bin/pg_dump/pg_dump.c (3)

247-247: LGTM!

The function declaration follows the established pattern of other dump functions in the codebase.


10517-10519: LGTM!

The DO_PACKAGE case follows the established pattern for handling different object types.


18745-18745: LGTM!

The DO_PACKAGE case is correctly placed in the switch statement.

src/backend/oracle_parser/ora_gram.y (2)

285-285: LGTM: Token and type declarations are well-structured

The new package-related tokens and semantic types are properly integrated into the grammar, following the existing patterns and conventions.

Also applies to: 727-727, 780-780, 797-797, 870-870


9977-9993: Verify package name validation and sharing clause implementation

A few points to verify:

  1. Ensure package names are validated against SQL identifier rules
  2. The opt_ora_sharing_clause usage needs implementation verification
✅ Verification successful

Let me gather more information about package name validation.


Let me search for package name validation rules.


Let me search for type_function_name definition since it's used by ora_func_name.


Based on the gathered information, I can now provide a final response about the package name validation and sharing clause implementation.

Package name validation and sharing clause are properly implemented

The verification shows:

  1. Package names are validated through ora_func_name rule which uses PostgreSQL's standard identifier validation:
    • Uses type_function_name which accepts standard SQL identifiers (IDENT)
    • Validates through check_func_name for qualified names
  2. The opt_ora_sharing_clause is properly defined with three valid options:
    • SHARING = METADATA
    • SHARING = NONE
    • Empty (no sharing clause)
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Search for opt_ora_sharing_clause definition and usage
rg "opt_ora_sharing_clause" -A 5

Length of output: 2598


Script:

#!/bin/bash
# Search for package name related rules and validation
rg "package_names" -A 5 src/backend/oracle_parser/ora_gram.y

# Search for any SQL identifier validation rules
ast-grep --pattern 'ColId:
  $$$'

Length of output: 84990


Script:

#!/bin/bash
# Search for ora_func_name definition and usage since package_names uses it
rg "ora_func_name" src/backend/oracle_parser/ora_gram.y -A 5

Length of output: 2987


Script:

#!/bin/bash
# Search for type_function_name definition and ColId usage
rg "type_function_name|ColId" src/backend/oracle_parser/ora_gram.y -A 5

Length of output: 19587

src/backend/parser/meson.build (1)

23-23: Verify the existence of parse_package.c

The addition follows the build system conventions. Let's verify that the source file exists and contains the expected package parsing implementation.

✅ Verification successful

From examining the output, I can see that parse_package.c exists and contains package-related functionality. The file header indicates it's part of the PLISQL Package parser implementation. Let's verify its content more specifically.


Based on the verification results, I can now provide a final response:

The source file parse_package.c exists and is properly integrated

The file exists and contains the expected package parsing implementation for PL/SQL packages. The file is:

  • Located at the correct path: src/backend/parser/parse_package.c
  • Contains proper copyright and identification headers
  • Includes necessary package-related functionality with proper integration into PostgreSQL's parser infrastructure
  • Has corresponding header file (parse_package.h) with well-defined interfaces for package types, variables, and functions
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify the existence and basic structure of parse_package.c

# Check if the file exists and contains expected package-related functions
fd parse_package.c -t f | xargs grep -l "package"

# Look for basic package parsing functions that should be present
ast-grep --pattern 'static Node *parse_package_$_'

Length of output: 75194


Script:

#!/bin/bash
# Check if parse_package.c exists and examine its content
fd parse_package.c -t f | xargs cat

# Look for package-related function declarations
ast-grep --pattern 'static Node *parse_package_$_'

# Look for package-related function declarations with different pattern
ast-grep --pattern 'Node *parse_package_$_'

Length of output: 75319


Script:

#!/bin/bash
# Check if parse_package.c exists and examine its basic structure
fd parse_package.c -t f | xargs head -n 20

# Look for package-related function declarations with a different pattern
ast-grep --pattern 'static PkgType *parse_package_type'

# Look for package-related function declarations with another pattern
ast-grep --pattern 'static PkgVar *parse_package_var'

Length of output: 65843


Script:

#!/bin/bash
# Look for package-related function declarations with a more specific pattern
rg -A 5 "parse_package\.[ch]" --type c

# Check for package-related header file
fd parse_package.h -t f | xargs cat

Length of output: 6346

src/backend/optimizer/plan/setrefs.c (1)

31-31: Include statement is appropriate

The inclusion of "utils/packagecache.h" is necessary for the new functionality and is correctly placed.

src/include/catalog/pg_package_body.h (3)

32-33: Ensure proper catalog annotations for 'pkgoid' field

The pkgoid field should have proper annotations to ensure correct catalog behavior. Verify that BKI_LOOKUP and other annotations are appropriate.

Please confirm that BKI_LOOKUP(pg_package) is correctly used and that pkgoid references the correct catalog.


49-52: Consistency in index naming and definitions

Ensure that index names and definitions follow the naming conventions and are consistent with existing catalog indexes.

Please verify that:

  • The index names pg_package_body_oid_index and pg_package_body_pkgoid_index are unique and follow the project's naming conventions.
  • The index definitions correctly reference the appropriate columns and use the correct operators.

54-55: Validate syscache definitions and number of attributes

Confirm that the MAKE_SYSCACHE macros have the correct number of attributes specified.

Ensure that the '8' in:

MAKE_SYSCACHE(PKGBODYOID, pg_package_body_oid_index, 8);
MAKE_SYSCACHE(PKGBODYPKGOID, pg_package_body_pkgoid_index, 8);

is the correct number of attributes for the syscache entries.

src/include/catalog/pg_package.h (3)

42-42: Check default value for 'pkgacl' field

Ensure that the default value for the pkgacl field is correctly set, and consider whether an explicit default is necessary.

Please confirm that:

  • The default value _null_ is appropriate for pkgacl.
  • If pkgacl should inherit default permissions, ensure that the default is set accordingly.

57-60: Consistency in index naming and definitions

Verify that the index names and definitions conform to naming conventions and correctly reference the columns.

Please check:

  • Index names pg_package_oid_index and pg_package_pkgname_nsp_index for uniqueness and adherence to naming standards.
  • Correct usage of operator classes in the index definitions.

62-63: Validate syscache definitions and number of attributes

Confirm that the MAKE_SYSCACHE macros have the correct parameters and attribute counts.

Ensure that:

  • The syscache entries PKGOID and PKGNAMEARGSNSP are correctly defined.
  • The attribute count (the '8' in the macros) is accurate.
src/include/parser/parse_package.h (2)

28-35: Ensure proper memory management for pointers in structures

In PkgType struct, ensure that pointers like item and value are properly managed to prevent memory leaks or dangling pointers.

Please confirm that:

  • The item pointer to PackageCacheItem and value pointer are correctly allocated and freed.
  • Appropriate reference counting or memory context management is in place.

58-79: Verify function declarations and parameter consistency

Ensure that the function declarations match their implementations and that parameter names and types are consistent.

Please check:

  • The correctness of function signatures for LookupPkgTypeByTypename, LookupPkgVarByvarnames, LookupPkgEntryByTypename, and LookupPkgFunc.
  • That LookupPkgFunc parameters align with existing conventions in similar parser functions.
src/include/utils/packagecache.h (3)

36-50: Ensure correctness in status flag definitions and macros

Confirm that the status flags and associated macros for PackageCacheStatus are correctly defined and used.

Please verify:

  • The bitwise operations in the macros are correct.
  • The flags do not conflict and are appropriately distinct.

61-70: Verify memory management in 'PackageCacheItem' struct

Ensure that the ctxt memory context and source pointer are properly managed to prevent memory leaks.

Please confirm:

  • That ctxt is appropriately allocated and freed.
  • That source data is managed within the ctxt memory context.

90-106: Ensure function prototypes match implementations

Verify that the function declarations match the definitions in the implementation files.

Please check:

  • Parameter types and return types are consistent.
  • Functions like ValidatroPackage (possible typo) should be correctly named, perhaps ValidatorPackage.
src/backend/access/common/session.c (2)

28-28: Include 'utils/dsa.h' for DSA functions

The inclusion of #include "utils/dsa.h" is appropriate for using DSA functions.


Line range hint 103-107: Ensure proper detachment and cleanup in 'DetachSession'

Confirm that all resources are properly released in DetachSession.

Please verify that:

  • The dsa_detach is called after dsm_detach.
  • Any additional cleanup required for the session is performed.
src/backend/parser/parse_package.c (2)

166-174: ⚠️ Potential issue

Check for Null item After PackageHandle Call

The PackageHandle function may return NULL, but the code does not check for this before using item, potentially leading to a null pointer dereference.

Add a null check after calling PackageHandle:

     if (PackageCacheIsValid(pkey, false))
         item = PackageCacheLookup(pkey);
     else
         item = PackageHandle(*pkey, false);

+    if (item == NULL)
+        return NULL;

Likely invalid or redundant comment.


75-80: ⚠️ Potential issue

Handle Unexpected List Sizes in Switch Statement

The switch statement on list_size does not handle cases where list_size is greater than 3. This could lead to unexpected behavior for larger lists.

Modify the switch statement to handle all possible cases or add a default case:

     switch (list_size)
     {
         case 0:
         case 1:
             /* doesn't support reference a package type exclude pkg name */
             return false;
+        default:
+            /* Handle cases where list_size > 3 appropriately */
+            break;
     }

Likely invalid or redundant comment.

src/backend/utils/cache/packagecache.c (2)

123-124: ⚠️ Potential issue

Add Null Check Before String Comparison

In package_resolve_names, first_name is used without checking if it's NULL, which could lead to a crash if list_length(names) is less than expected.

Add a null check for first_name:

+    if (first_name == NULL)
+        return false;

     if (strcmp(first_name, get_database_name(MyDatabaseId)) == 0)

Likely invalid or redundant comment.


82-110: ⚠️ Potential issue

Missing Resource Release in PackageCacheIsValid

The function PackageCacheIsValid may return early without releasing the cache tuple if tuple is not valid, leading to a resource leak.

Ensure that ReleaseSysCache(tuple); is called before any return statement after SearchSysCache1:

     if (!HeapTupleIsValid(tuple))
+    {
+        ReleaseSysCache(tuple);
         return false;
+    }

Likely invalid or redundant comment.

src/backend/parser/parse_type.c (1)

238-246: Impact of Unconditional Package Type Lookup

Introducing LookupPkgTypeByTypename unconditionally in LookupTypeNameOid might affect the behavior of type lookups, especially if package types are not intended to be used in all contexts.

Please verify that this change does not adversely affect existing type lookup logic when package types are not involved.

src/backend/commands/alter.c (1)

Line range hint 659-783: Comprehensive Dependency Handling When Altering Package Schema

When changing the schema of a package in ExecAlterObjectSchemaStmt and AlterObjectNamespace_internal, all dependencies and references to the package need to be updated accordingly.

Ensure that altering a package's schema updates all dependencies, and that no orphaned references remain.

src/backend/oracle_parser/liboracle_parser.c (2)

704-706: Ensure Correct Token Length Calculation for PACKAGE

The cur_token_length for the PACKAGE token is set to 7. Verify that this length calculation accurately reflects the token length, especially if there are any changes to the token definitions elsewhere.


779-784: Handle PACKAGE BODY Token Appropriately

The logic replaces PACKAGE with PACKAGE_BODY when followed by BODY. Ensure that the PACKAGE_BODY token is correctly defined and handled in all relevant parts of the parser and that this change does not affect existing functionality related to the PACKAGE token.

src/backend/catalog/pg_proc.c (1)

359-368: Check for Proper Handling of New Catalog Attributes

The new attributes protypenames and rettypename are being set based on parametertypeNames and rettypeName. Verify that these attributes are correctly defined in the system catalog and that they interact properly with existing attributes.

src/backend/commands/packagecmds.c (1)

870-872: ⚠️ Potential issue

Null Pointer Check for tuple

Ensure that tuple is checked for NULL before dereferencing it. Although you have an error check, it's important to handle the possibility of a NULL return from SearchSysCache1 to prevent potential null pointer dereferences.

Apply this diff to add a null check:

 if (!HeapTupleIsValid(tuple))
     ereport(ERROR,
             (errcode(ERRCODE_UNDEFINED_OBJECT),
              errmsg("package body with OID %u does not exist", bodyid)));

+ if (tuple == NULL)
+     elog(ERROR, "Failed to find package body with OID %u", bodyid);

 pkgOid = ((Form_pg_package_body) GETSTRUCT(tuple))->pkgoid;

Likely invalid or redundant comment.

src/backend/utils/fmgr/funcapi.c (2)

1476-1478: Verify Usage of repl_func_real_argtype

The function repl_func_real_argtype is called to possibly replace argument types from a package. Ensure that this function handles all necessary cases and that it correctly modifies *p_argtypes as intended.


1863-1907: ⚠️ Potential issue

Missing Null Checks in get_func_typename_info

In the function get_func_typename_info, there are potential missing null checks after SysCacheGetAttr calls. If these calls return NULL, accessing the results could lead to null pointer dereferences. Ensure that p_argtypeNames and rettypeName are only used when not NULL.

Apply this diff to add null checks:

if (p_argtypeNames != NULL)
{
    protypenames = SysCacheGetAttr(PROCOID, procTup,
                                   Anum_pg_proc_protypenames,
                                   &isNull);
    if (!isNull)
    {
        // Existing code to process protypenames
    }
+   else
+   {
+       *p_argtypeNames = NULL;
+   }
}

if (rettypeName != NULL)
{
    prorettypename = SysCacheGetAttr(PROCOID, procTup,
                                     Anum_pg_proc_rettypename,
                                     &isNull);
    if (!isNull)
    {
        *rettypeName = TextDatumGetCString(prorettypename);
    }
+   else
+   {
+       *rettypeName = NULL;
+   }
}

Likely invalid or redundant comment.

src/backend/utils/cache/plancache.c (2)

1749-1761: Add new function setPlanCacheInvalidForPackage to invalidate plans referencing a package

This new function computes a hash value for the given package OID and calls PlanCacheObjectCallback to invalidate any plans that depend on that package. This is important to ensure cached plans are refreshed when a package is modified.


1763-1771: Add new callback PlanCachePackageBodyCallback to invalidate plans on package body changes

This callback is registered to handle invalidation when a package body is modified. Since the hash value cannot be matched in this case, it calls PlanCacheObjectCallback with a hash value of 0 to invalidate all plans referencing the package. This comprehensive invalidation is necessary since the specific changes in the package body are unknown.

src/include/nodes/primnodes.h (3)

743-744: Add new macros to identify function types related to packages

The new macros FUNC_FROM_PACKAGE and FUNC_FROM_PACKGE_INITBODY allow identifying functions originating from packages. This is important metadata to track the source of functions.


747-752: Update FUNC_EXPR_FROM_PG_PROC macro to handle new package function types

The macro is updated to return false for the new package function types FUNC_FROM_PACKAGE and FUNC_FROM_PACKGE_INITBODY. This ensures the macro correctly differentiates between regular and package functions.


785-787: Add new fields to FuncExpr structure for package-related metadata

The FuncExpr structure is extended with fields function_name, ref_pkgtype, and pkgoid to store the package-related metadata such as the function name used in a package, whether it references a package type, and the package's OID. This allows tracking important information for package functions.

src/backend/commands/functioncmds.c (6)

92-93: Add rettypename parameter to compute_return_type function

The function signature is updated to return the name of the return type via the new rettypename output parameter. This allows capturing the return type name for package functions.


100-128: Look up return type from package for PL/SQL functions

For PL/SQL functions, the code first attempts to look up the return type from a package using LookupPkgTypeByTypename. If a package type is found, it updates the return type details accordingly, including prepending the package schema name if needed. This ensures package return types are correctly resolved.


230-231: Add parametertypeNames parameter to interpret_function_parameter_list

The function signature is extended with the parametertypeNames output parameter to collect the names of the parameter types. This is used for package function parameters.


258-266: Allocate array for parameter type names for PL/SQL functions

For PL/SQL functions, an array typeNames is allocated to store the parameter type names. This is necessary to handle package types used as function parameters.


285-351: Look up parameter types from packages for PL/SQL functions

Similar to the return type handling, the code attempts to resolve parameter types from packages for PL/SQL functions. If a package type is found, it updates the parameter type details and stores the type names. Appropriate error handling is added for undefined types.


567-583: Build array of parameter type names for package types

If any package types were found in the function parameters, the code builds an array parametertypeNames containing their names. This array is returned to the caller to provide information about package type parameters.

src/backend/parser/parse_func.c (3)

285-301: Look up functions in packages if regular lookup fails

If the initial function lookup fails and the function name is a single identifier, the code attempts to look it up as a package function by prepending a "standard" prefix to the name. If a package function is found, the pkgoid is set in the FuncExpr node. This allows resolving functions defined in packages.


303-315: Perform package function lookup if subproc hook lookup fails

If the subproc hook lookup fails to find the function, the code falls back to a package function lookup using LookupPkgFunc. If successful, the function is marked as originating from a package. This provides a secondary lookup mechanism for package functions.


812-847: Set package-related fields in FuncExpr node

The pkgoid field is set to the resolved package OID. If the function is from a package, additional fields like function_name are populated based on the package details. For regular functions, a check is added to see if any argument or return types come from a package, in which case ref_pkgtype is set to true. This metadata is important for tracking package dependencies and origins of types.

src/backend/catalog/dependency.c (4)

68-70: Ensure proper ordering and necessity of new header files

The inclusion of pg_package.h, pg_package_body.h, and packagecmds.h adds necessary definitions for package management support. Verify that these headers are required and that their inclusion follows the project's convention for header file ordering and grouping.


150-198: Update object_classes array with new package-related entries

The object_classes array now includes PackageRelationId and PackageBodyRelationId, which map OCLASS_PACKAGE and OCLASS_PACKAGE_BODY to their respective catalog OIDs. This update is essential for managing dependencies involving packages and their bodies.


90-91: Confirm the necessity of including packagecache.h

The addition of #include "utils/packagecache.h" suggests that the file utilizes caching mechanisms for packages. Ensure that functions or definitions from packagecache.h are indeed used in this file. If not, consider removing this inclusion to avoid unnecessary dependencies.

Run the following script to check for usages of packagecache.h:


1445-1452: ⚠️ Potential issue

Handle deletion of package and package body objects

In the doDeletion function, cases for PackageRelationId and PackageBodyRelationId have been added to handle the deletion of packages and package bodies by invoking DropPackageById and DropPackageBodyById respectively.

Ensure that DropPackageById and DropPackageBodyById properly handle all necessary checks, such as permission verification and dependency management. Additionally, confirm that these functions correctly release any allocated resources to prevent memory leaks or dangling pointers.

Run the following script to verify the implementations:

✅ Verification successful

Based on the gathered information, I can now provide a final response:

Permission checks and resource management are properly handled in package operations

The implementation shows that both DropPackageById and DropPackageBodyById functions are well-integrated with the system's permission and resource management:

  1. Permission checks:

    • Package operations are protected by pg_package_aclcheck which verifies execution privileges
    • Row-level locking is properly handled using RowExclusiveLock
  2. Memory management:

    • Package cache is properly freed using FreePackageCache
    • System catalog resources are released with ReleaseSysCache
    • Table resources are properly closed with table_close
  3. Dependency management:

    • Package dependencies are tracked through the dependency system
    • Owner dependencies are recorded via recordDependencyOnOwner
    • ACL dependencies are handled through recordDependencyOnNewAcl
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Check if `DropPackageById` and `DropPackageBodyById` handle permissions and dependencies

# Search for the definitions and check for permission and dependency handling
ast-grep --pattern $'void DropPackageById(Oid packageId) {
  $$$
  /* Expected: Check permissions */
  /* Expected: Manage dependencies */
  $$$
}' src/backend/commands/packagecmds.c

ast-grep --pattern $'void DropPackageBodyById(Oid packageBodyId) {
  $$$
  /* Expected: Check permissions */
  /* Expected: Manage dependencies */
  $$$
}' src/backend/commands/packagecmds.c

Length of output: 375


Script:

#!/bin/bash
# Let's try a different approach to find these functions and their implementations

# First, let's check if the file exists
fd "packagecmds.c" --type f

# Then, let's use ripgrep to find the function definitions with context
rg "DropPackageById|DropPackageBodyById" -A 20

# Also search for any related permission checks
rg "aclcheck|ACL_|ACLCHECK_" --type c

# And search for memory management related calls
rg "pfree|palloc|MemoryContext" -A 2 --type c

Length of output: 65946


Script:

#!/bin/bash
# Let's search for the implementation details of these functions
# and their dependencies

# Search for package-related functions
rg "DropPackage|FreePackageCache" -A 5 --type c

# Search for package-related permission checks
rg "pg_package_aclcheck" -A 5 --type c

# Search for package-related memory management
rg "package.*cache" -A 5 --type c

# Search for package-related dependency management
rg "recordDependencyOn.*Package" -A 5 --type c

Length of output: 23238

src/backend/tcop/utility.c (8)

59-59: Include packagecmds.h for package command support

The inclusion of "commands/packagecmds.h" is necessary to provide declarations for package-related command functions. Ensure that this header is included in the correct order according to the project's coding standards.


179-181: Classify package commands as non-read-only

The ClassifyUtilityCommandAsReadOnly function now includes cases for T_CreatePackageStmt, T_CreatePackageBodyStmt, and T_AlterPackageStmt. This correctly classifies package-related commands as not read-only, which is essential for the database's consistency and security.


1922-1931: Add handling for package commands in ProcessUtilitySlow

Package commands are now properly handled in the ProcessUtilitySlow function, with cases added for:

  • T_CreatePackageStmt calling CreatePackage
  • T_CreatePackageBodyStmt calling CreatePackageBody
  • T_AlterPackageStmt calling AlterPackage

2360-2362: Add command tag for ALTER PACKAGE operation

In the AlterObjectTypeCommandTag function, a new case for OBJECT_PACKAGE has been added, mapping to CMDTAG_ALTER_PACKAGE. This ensures that ALTER PACKAGE commands are correctly tagged and logged.


2671-2676: Include command tags for dropping packages

The CreateCommandTag function now includes cases for OBJECT_PACKAGE and OBJECT_PACKAGE_BODY, mapping to CMDTAG_DROP_PACKAGE and CMDTAG_DROP_PACKAGE_BODY respectively. This addition ensures that drop operations for packages are correctly identified and handled.


3263-3272: Add command tags for package creation and alteration

The CreateCommandTag function has been updated to include:

  • T_CreatePackageStmt mapping to CMDTAG_CREATE_PACKAGE
  • T_CreatePackageBodyStmt mapping to CMDTAG_CREATE_PACKAGE_BODY
  • T_AlterPackageStmt mapping to CMDTAG_ALTER_PACKAGE

This ensures that package-related commands are properly tagged for logging and processing.


3807-3812: Set appropriate log levels for package commands

In GetCommandLogLevel, the package commands are assigned a log level of LOGSTMT_DDL. This is appropriate as these commands are data definition language operations and should be logged accordingly.


2970-2972: Handle DISCARD PACKAGES in DiscardStmt

A new case DISCARD_PACKAGES has been added to the DiscardStmt handling. This allows the DISCARD command to properly handle the cleanup of package-related resources.

Run the following script to verify that DiscardCommand correctly handles DISCARD_PACKAGES:

src/backend/utils/cache/lsyscache.c (5)

53-54: Include necessary headers for package support

The inclusion of "funcapi.h" and "parser/parse_package.h" provides necessary function APIs and package parsing capabilities. Ensure these headers are required and included according to the project's header inclusion guidelines.


1668-1673: Modify get_func_rettype to use get_func_real_rettype

The get_func_rettype function now calls get_func_real_rettype to obtain the actual return type, especially when dealing with package variables in Oracle compatibility mode. This change ensures that the function's return type is accurate in different compatibility settings.


Line range hint 1868-1913: Update get_func_signature to reflect real return and argument types

In get_func_signature, the function now retrieves the real return type using get_func_real_rettype and updates the argument types with repl_func_real_argtype. This change ensures that the function signature is accurate, especially when types are affected by package variables in Oracle compatibility mode.


Line range hint 1914-1931: Verify proper handling of function variadic types and return sets

Ensure that get_func_variadictype and get_func_retset correctly handle functions with variadic arguments and those that return sets, respectively. Changes in the function type retrieval may affect these behaviors.

Run the following script to test functions with variadic arguments and return sets:

✅ Verification successful

Both functions correctly handle their respective type checks with proper cache management

The verification shows that both functions follow the correct pattern for accessing system catalog information:

  1. get_func_variadictype properly retrieves the provariadic field from the function's system catalog entry using GETSTRUCT and releases the cache.
  2. get_func_retset correctly accesses the proretset field and follows the same cache management pattern.

Both implementations include proper error handling for invalid cache lookups and maintain consistent cache cleanup through ReleaseSysCache.

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify handling of variadic functions and functions returning sets

# Test functions with variadic arguments
ast-grep --pattern $'Oid get_func_variadictype(Oid funcid) {
  $$$
}' src/backend/utils/cache/lsyscache.c

# Test functions that return sets
ast-grep --pattern $'bool get_func_retset(Oid funcid) {
  $$$
}' src/backend/utils/cache/lsyscache.c

Length of output: 1979


1708-1867: 🛠️ Refactor suggestion

⚠️ Potential issue

Implement repl_func_real_argtype to replace function argument types

The function repl_func_real_argtype updates the argument types of a function to their actual types, considering package variables in Oracle compatibility mode. This ensures that the function signature accurately reflects any dynamic types influenced by packages.

There is a potential for buffer overruns in the loops starting at line 1766 and line 1841. Ensure that array bounds are checked when accessing p_argtypeNames and other arrays to prevent reading beyond their allocated memory.

Add checks to validate array indices before accessing array elements.

for (i = 0; i < numargs; i++)
{
+   if (i >= numargs) // Ensure we are within bounds
+       break;

    /* existing code */
}

Likely invalid or redundant comment.

src/backend/catalog/namespace.c (3)

44-45: Include necessary headers for package management

The addition of #include "catalog/pg_package.h" and #include "commands/packagecmds.h" is appropriate to support package management functionalities.


52-52: Include parser header for package parsing

Including parse_package.h is necessary for parsing package-related SQL commands.


5094-5104: Ensure consistency with pg_*_is_visible functions

The implementation of pg_package_is_visible is consistent with other pg_*_is_visible functions, correctly checking the existence of the package and returning the visibility status.

src/backend/commands/typecmds.c (1)

1790-1793: Ensure updated function calls match new signature

The function call to ProcedureCreate in makeRangeConstructors includes the new parameters as per the updated function signature. This ensures compatibility and correctness.

src/include/nodes/parsenodes.h (1)

2317-2318: Addition of OBJECT_PACKAGE and OBJECT_PACKAGE_BODY to ObjectType enum.

The addition of OBJECT_PACKAGE and OBJECT_PACKAGE_BODY to the ObjectType enumeration expands the supported object types, enabling package-related functionalities.

src/backend/catalog/aclchk.c (2)

2303-2303: ⚠️ Potential issue

Verify the use of NameStr with pg_package_tuple->pkgname.

Ensure that pg_package_tuple->pkgname is of type NameData before using NameStr macro. If pkgname is not NameData, accessing it with NameStr may lead to incorrect behavior.

Apply this diff to correct the usage if necessary:

-    									 NameStr(pg_package_tuple->pkgname),
+    									 TextDatumGetCString(pg_package_tuple->pkgname),

Run the following script to check the data type of pkgname in pg_package:

✅ Verification successful

The usage of NameStr with pg_package_tuple->pkgname is correct

From the pg_package.h definition, we can see that pkgname is explicitly defined as NameData pkgname in the FormData_pg_package structure. This confirms that pg_package_tuple->pkgname is of type NameData, making the usage of NameStr macro appropriate and safe in this context.

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify the data type of pkgname in pg_package.

# Search for the definition of Form_pg_package
rg -A 5 'typedef struct FormData_pg_package' src/include/catalog/pg_package.h

# Check the declaration of pkgname
rg 'pg_catalog\.name\s+pkgname' src/include/catalog/pg_package.h

Length of output: 255


Script:

#!/bin/bash
# Let's try a different approach to find the structure definition and type of pkgname

# Search for pkgname in pg_package.h with more context
rg -A 10 'pg_package' src/include/catalog/pg_package.h

# Also check for NameData type definition which is commonly used with NameStr
rg 'typedef.*NameData' src/include/c.h

# Look for the actual usage context of pg_package_tuple
rg -B 2 -A 2 'pg_package_tuple.*pkgname' src/backend/catalog/

Length of output: 2190


2323-2327: Ensure proper zero-initialization of arrays before use.

The arrays values, nulls, and replaces are stack-allocated but may not be zero-initialized in all contexts. Confirm that MemSet or memset correctly initializes the entire arrays.

Run the following script to ensure MemSet is correctly used for array initialization:

✅ Verification successful

Arrays are properly initialized, no issues found

The code shows consistent and correct initialization patterns throughout aclchk.c:

  • All three arrays (values, nulls, and replaces) are properly initialized using MemSet before use
  • The initialization sequence is:
MemSet(values, 0, sizeof(values));
MemSet(nulls, false, sizeof(nulls));
MemSet(replaces, false, sizeof(replaces));
  • This pattern is consistently used across multiple functions in the file, and in some cases the arrays are even initialized at declaration time with = {0}
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Check for proper usage of MemSet or memset for array initialization.

# Search for MemSet and memset usage in the codebase
rg 'MemSet\((\w+),\s*(0|false),\s*sizeof\(\1\)\)' src/
rg 'memset\((\w+),\s*(0|false),\s*sizeof\(\1\)\)' src/

Length of output: 613


Script:

#!/bin/bash
# Description: Check for proper usage of MemSet or memset for array initialization
# Using simpler pattern matching without backreferences

# Search for array initialization context around the specific line
rg -B 10 -A 10 "MemSet\(replaces, false, sizeof\(replaces\)\)" src/backend/catalog/aclchk.c

# Look for declarations and initializations of values and nulls arrays
rg -B 5 -A 5 "bool\s+replaces\[|Datum\s+values\[|bool\s+nulls\[" src/backend/catalog/aclchk.c

Length of output: 4195

src/backend/catalog/objectaddress.c (4)

642-669: Add handling for new object types OBJECT_PACKAGE and OBJECT_PACKAGE_BODY.

The changes add new entries to the ObjectProperty array for the OBJECT_PACKAGE and OBJECT_PACKAGE_BODY object types. This allows the get_object_address() function to handle these new types when looking up object addresses.


2607-2619: Add ownership checks for OBJECT_PACKAGE and OBJECT_PACKAGE_BODY.

The check_object_ownership() function is updated to handle the new OBJECT_PACKAGE and OBJECT_PACKAGE_BODY types. It calls the appropriate ownership check functions pg_package_ownercheck() and pg_packagebody_ownercheck() for these types.


4081-4107: Add cases to handle OBJECT_PACKAGE and OBJECT_PACKAGE_BODY in getObjectDescription().

The getObjectDescription() function is extended to handle the new object types. For OBJECT_PACKAGE, it retrieves the package name and schema using get_package_nameinfo(). For OBJECT_PACKAGE_BODY, it uses get_package_nameinfo_bybodyid() to get the package name and schema based on the package body OID.


5995-6025: Add cases to handle OBJECT_PACKAGE and OBJECT_PACKAGE_BODY in getObjectIdentityParts().

Similar to the changes in getObjectDescription(), the getObjectIdentityParts() function is updated to handle the new object types. It retrieves the package name and schema for OBJECT_PACKAGE and OBJECT_PACKAGE_BODY using the respective helper functions.

src/backend/optimizer/util/clauses.c (5)

2612-2616: Set package type information for function expressions.

In the simplify_function() function, a new check is added for function expressions that come from a package. If the ref_pkgtype flag is set, the set_pkgtype_from_funcexpr() function is called to set the package type information for the function expression.


2630-2632: Set package information for function expressions.

Another check is added in simplify_function() to set the package information for function expressions that come from a package. The set_pkginfo_from_funcexpr() function is called to populate the package-related fields in the FuncExpr node.


4387-4396: Replace function argument types with real types for package functions.

In the expand_function_arguments() function, a new block of code is added specifically for the Oracle compatibility mode. It creates a copy of the proargtypes array and calls repl_func_real_argtype() to replace the argument types with the real types for functions that belong to a package.


4584-4586: Get the real return type of a function.

The get_func_real_rettype() function is used to retrieve the real return type of a function from its pg_proc tuple. This ensures that the correct return type is used for functions that belong to a package.


5362-5363: Get the real return type of a function.

Similar to the previous change, the get_func_real_rettype() function is used to get the real return type of a function when checking if it returns RECORD in the inline_set_returning_function() function.

src/backend/utils/adt/ruleutils.c (2)

3429-3526: Verify error handling for invalid package OID.

The function looks up the pg_package tuple using the given package OID. It throws an error if the tuple is not found. This error handling looks appropriate.


3462-3464: Verify the DEFAULT COLLATION clause generation.

The DEFAULT COLLATION clause is generated if pkg_form->use_collation is true. The hardcoded collation name "USING_NLS_COMP" is used. Ensure this is the correct behavior and consider making the collation name configurable if needed.

src/backend/utils/cache/meson.build (1)

18-18: LGTM! Verify related cache implementation files.

The addition of packagecache.c to backend sources is consistent with the caching infrastructure.

Let's verify the existence and structure of related cache implementation files:

✅ Verification successful

LGTM! Package cache implementation is properly structured and integrated

The verification confirms:

  • Both implementation (packagecache.c) and header (packagecache.h) files exist in their expected locations
  • The cache implementation follows a consistent pattern with:
    • Well-defined cache structures (PackageCacheItem, PackageCacheEntry)
    • Standard cache operations (PackageCacheLookup, PackageCacheInsert)
    • Proper integration with PL/SQL package functionality in pl_package.c
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify the existence and basic structure of package cache files

# Check if the implementation file exists
fd -t f "packagecache.c" src/backend/utils/cache/

# Check if the header file exists
fd -t f "packagecache.h" src/include/utils/

# Verify basic structure of cache implementation
rg -A 5 "struct\s+PackageCache|PackageCacheLookup|PackageCacheInsert" 

Length of output: 7596

src/backend/utils/cache/Makefile (1)

29-30: LGTM! Object file addition is consistent.

The addition of packagecache.o to OBJS aligns with the source file addition in meson.build.

src/backend/commands/meson.build (1)

53-53: LGTM! Verify package command implementation.

The addition of packagecmds.c to backend sources is consistent with the command handling infrastructure.

Let's verify the package command implementation:

✅ Verification successful

Package command implementation is properly integrated

Based on the verification results:

  • The package command implementation file packagecmds.c exists and is properly added to the build
  • Command handlers for Create/Alter package operations are registered in utility.c
  • Package-related error handling and catalog definitions are in place
  • Package functionality has test coverage (evident from error messages in test files)
  • The implementation includes proper permission checks and validation logic

The addition of packagecmds.c to backend sources is well-integrated with:

  • Command processing infrastructure
  • Catalog management
  • Error handling
  • Access control checks
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify package command implementation structure

# Check if the implementation file exists
fd -t f "packagecmds.c" src/backend/commands/

# Verify command handler registration
rg -A 5 "CreatePackageStmt|AlterPackageStmt|DropPackageStmt" 

# Check for package-related GUC parameters
rg "package" src/backend/utils/misc/guc.c

Length of output: 7180


Script:

#!/bin/bash
# Let's verify the implementation details of the package commands

# Check the actual implementation of package commands
ast-grep --pattern 'CreatePackage($$$) {
  $$$
}'

# Check for package-related error messages and catalog definitions
rg "ERROR.*package" src/
rg "CATALOG.*package" src/

# Check for package-related test files
fd -t f "package.*test" -e "sql"

Length of output: 9978

src/include/commands/packagecmds.h (1)

25-27: Verify transaction and permission handling in package operations

The create/alter operations and ownership checks should be properly integrated with PostgreSQL's transaction and permission systems.

Also applies to: 31-32

✅ Verification successful

Let me gather more information about transaction handling since the previous search didn't show transaction-related patterns.


Let me check one more aspect to see how these operations are integrated with PostgreSQL's standard command processing.


Package operations have proper security and transaction handling

The code shows appropriate integration with PostgreSQL's security and transaction systems:

  • ACL checks are properly implemented for schema, language, and package ownership
  • Command counter increments are used to handle transaction visibility
  • Object dependencies are correctly recorded
  • Proper error handling for permission violations is in place

The implementation follows PostgreSQL's standard patterns for DDL operations, including:

  • Owner checks using aclcheck_error
  • Namespace permission verification
  • Transaction visibility management with CommandCounterIncrement
  • Object dependency tracking with recordDependencyOn* functions
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Search for transaction and permission handling patterns
rg -A 3 "BeginInternalSubTransaction|CommitTransactionCommand|AbortCurrentTransaction" src/backend/commands/packagecmds.c

# Check for proper ACL checks
rg -A 3 "aclcheck|pg_namespace_aclcheck" src/backend/commands/packagecmds.c

Length of output: 1479


Script:

#!/bin/bash
# Search for transaction handling in internal functions
ast-grep --pattern 'ObjectAddress CreatePackage_internal($$$)' src/backend/commands/packagecmds.c

# Look for other transaction-related functions
rg "StartTransactionCommand|CommitTransactionCommand|BeginTransactionBlock|EndTransactionBlock" src/backend/commands/packagecmds.c

# Check if these commands are wrapped in a transaction block
rg -B 2 -A 5 "CreatePackage_internal|CreatePackageBody_internal|AlterPackage_internal" src/backend/commands/packagecmds.c

Length of output: 1906


Script:

#!/bin/bash
# Check if these operations are properly integrated with standard command processing
rg -B 2 -A 5 "ProcessUtility.*package" src/backend/tcop/

# Look for standard transaction handling patterns in the utility command processing
rg "CommandCounterIncrement|RegisterCreatedObjectsInNamespaces" src/backend/commands/packagecmds.c

# Check for proper object dependency handling
rg "recordDependencyOn|recordDependencyOnOwner" src/backend/commands/packagecmds.c

Length of output: 642

src/backend/commands/Makefile (1)

64-65: LGTM: Proper integration of package commands

The addition of packagecmds.o follows the established pattern and maintains alphabetical ordering.

src/backend/commands/discard.c (3)

24-24: LGTM: Include statement properly placed

The include statement for packagecache.h is correctly placed in the utils includes section.


49-52: LGTM: DISCARD PACKAGES implementation

The implementation follows the established pattern for DISCARD commands and correctly handles package cache reset.


84-84: LGTM: Package cache reset in DiscardAll

ResetPackageCaches() is appropriately added to DiscardAll alongside other cache resets.

src/include/parser/parse_type.h (1)

36-36: LGTM: New type name formatting function

The TypeNameToQuoteString function declaration follows the established pattern and is properly placed alongside related functions.

src/backend/oracle_parser/ora_gramparse.h (1)

39-40: LGTM! Package-related enum values are properly integrated.

The addition of OraBody_PACKAGE and OraBody_PACKAGEBODY to OraBodyStyle enum is well-placed and consistent with the existing structure. These values are essential for distinguishing between package declarations and their implementations.

src/bin/psql/describe.h (1)

37-39: LGTM! Package description function follows established patterns.

The describePackages function declaration maintains consistency with other describe functions in terms of:

  • Parameter types and names
  • Return type
  • Documentation style
  • Function naming convention
src/include/catalog/meson.build (1)

72-73: Verify catalog header ordering dependencies.

While the addition of pg_package.h and pg_package_body.h appears correct, the file comment indicates there are ordering dependencies for catalog headers. Please verify that:

  1. These new catalogs don't need to appear before any existing ones
  2. There are no dependencies between pg_package.h and pg_package_body.h that would require a specific order
✅ Verification successful

Catalog header ordering is correct

The verification shows that:

  1. pg_package_body has a foreign key dependency on pg_package (via BKI_LOOKUP(pg_package)), which means pg_package.h must be listed before pg_package_body.h in the build file.
  2. Neither catalog is marked as BKI_BOOTSTRAP, indicating they don't need special early initialization.
  3. The current ordering in meson.build correctly places pg_package.h before pg_package_body.h, satisfying the dependency requirement.
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Check for potential ordering dependencies in catalog headers

# Search for references to pg_package in other catalog headers
echo "Checking for references to pg_package in other catalog headers:"
rg -l "pg_package" --type cpp

# Look for BKI_BOOTSTRAP or similar markers in the new catalog headers
echo "Checking for BKI_BOOTSTRAP markers:"
rg "BKI_BOOTSTRAP" pg_package.h pg_package_body.h

# Check for foreign key relationships
echo "Checking for foreign key relationships:"
rg "FOREIGN_KEY" pg_package.h pg_package_body.h

Length of output: 819


Script:

#!/bin/bash
# Let's check the actual catalog header files in their correct location
echo "Checking catalog headers content:"
cat src/include/catalog/pg_package.h src/include/catalog/pg_package_body.h

# Check for any ordering comments in the catalog directory
echo -e "\nChecking for ordering comments in catalog directory:"
rg -i "order" src/include/catalog/

# Check for dependencies between package and package_body
echo -e "\nChecking for dependencies between package and package_body:"
rg "package" src/include/catalog/pg_package.h src/include/catalog/pg_package_body.h

# Check for any foreign key or bootstrap declarations
echo -e "\nChecking for foreign keys and bootstrap declarations:"
rg -e "FOREIGN" -e "BKI_" src/include/catalog/pg_package.h src/include/catalog/pg_package_body.h

Length of output: 13076

src/include/catalog/Makefile (1)

84-86: Verify catalog header ordering dependencies

The placement of new catalog headers needs verification as the comment states that "BKI_BOOTSTRAP catalogs must appear first, and pg_statistic before pg_statistic_ext_data, and there are reputedly other, undocumented ordering dependencies."

✅ Verification successful

Let me gather more information about the catalog headers ordering by examining the Makefile and related comments.


Based on the gathered information, I can now provide the final response:

Catalog header ordering is correctly maintained

The new package-related headers (pg_package.h and pg_package_body.h) are appropriately placed at the end of the catalog headers list. This is safe because:

  • Neither of them has BKI_BOOTSTRAP marking
  • They are placed after pg_statistic and pg_statistic_ext_data (which have documented ordering requirements)
  • pg_package_body.h correctly follows pg_package.h as it has a dependency on it (BKI_LOOKUP reference)
  • The removal of pg_subscription_rel.h and addition of new headers at the end maintains all documented ordering requirements
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Check if any of the removed or added catalog headers have BKI_BOOTSTRAP
# or other ordering dependencies.

# Check for BKI_BOOTSTRAP in the new and removed files
echo "Checking for BKI_BOOTSTRAP and dependencies..."
rg "BKI_BOOTSTRAP" src/include/catalog/pg_package.h src/include/catalog/pg_package_body.h

# Check references to subscription_rel to understand impact of removal
echo "Checking references to subscription_rel..."
rg -l "subscription_rel" --type cpp

Length of output: 365


Script:

#!/bin/bash
# Check the Makefile and comments about catalog ordering
echo "Checking Makefile for catalog ordering comments..."
cat src/include/catalog/Makefile

# List all catalog headers to understand the full ordering context
echo -e "\nListing all catalog headers..."
fd "pg_.*\.h$" src/include/catalog/

# Check if pg_package or pg_package_body are referenced by other catalogs
echo -e "\nChecking references to new package catalogs..."
rg "pg_package" --type cpp

Length of output: 11818

src/include/catalog/pg_proc.h (1)

114-117: Clarify NOT NULL constraint implementation

The comment states these fields are "NOT NULL for package types", but they use BKI_DEFAULT(_null_). This seems contradictory. Consider:

  1. Adding explicit validation in the code
  2. Documenting how this constraint is enforced
  3. Adding a check constraint in the catalog
✅ Verification successful

BKI_DEFAULT(null) is consistent with package type requirements

The use of BKI_DEFAULT(_null_) for rettypename and protypenames is consistent with how nullable catalog fields are handled in PostgreSQL. The NOT NULL constraint for package types is enforced at runtime through function validation code, as evidenced by:

  1. Similar pattern used across catalog tables for nullable fields that may have runtime constraints (e.g., pg_type.h, pg_proc.h)
  2. Package type validation is handled in function commands code (functioncmds.c) where package type checks are performed
  3. The BKI_DEFAULT(null) is the standard way to initialize catalog fields that may be NULL in some cases but required in others
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Check how NOT NULL constraints are implemented for package types

# Look for validation code
echo "Checking for validation implementation..."
rg "rettypename|protypenames" --type cpp

# Look for similar patterns in other catalog definitions
echo "Checking for similar patterns in other catalogs..."
rg "NOT NULL.*BKI_DEFAULT\(_null_\)" src/include/catalog/

Length of output: 450


Script:

#!/bin/bash
# Let's check for package type validation patterns and related code

# Look for package type validation code
echo "Searching for package type validation..."
rg "package.*type" -B2 -A2 --type cpp

# Check for validation in ProcedureCreate
echo "Checking ProcedureCreate implementation..."
ast-grep --pattern 'ProcedureCreate($$$)'

# Look for NOT NULL constraint implementations in catalog code
echo "Checking catalog constraint patterns..."
rg "check.*constraint|validate.*constraint" --type cpp src/backend/catalog/

# Search for package type related functions
echo "Searching for package type related functions..."
rg "package.*type|is_package" --type cpp

Length of output: 66377


Script:

#!/bin/bash
# Let's check for package type validation in PL/SQL package code

# Look for package type validation in pl_package files
echo "Searching for package type validation in pl_package..."
rg "package.*type.*validation|package.*type.*null" src/pl/plisql/src/pl_package.*

# Check for type validation in package-related code
echo "Checking package type validation in catalog code..."
rg "package.*type.*check|package.*type.*validate" src/backend/catalog/

# Look for package type constraint handling
echo "Searching for package type constraint handling..."
ast-grep --pattern 'if ($_ && $_->package_type) {
  $$$
}'

Length of output: 2035


Script:

#!/bin/bash
# Let's check how package types are handled in the codebase

# Look for package type handling in procedure creation/modification code
echo "Checking package type handling in procedure code..."
rg "package.*type|rettypename|protypenames" src/backend/commands/

# Search for package type validation in type-related code
echo "Searching type validation code..."
rg "typname|type.*validate|type.*check" src/backend/catalog/pg_type*

# Look for BKI_DEFAULT handling
echo "Checking BKI_DEFAULT handling..."
rg "BKI_DEFAULT.*_null_" src/include/catalog/

Length of output: 4562

src/backend/access/index/amvalidate.c (2)

28-29: LGTM! Include directive properly placed.

The addition of lsyscache.h is appropriate for accessing get_func_real_rettype.


168-169: LGTM! Improved return type validation.

The change to use get_func_real_rettype enhances type checking by considering the actual return type instead of just the declared type.

src/include/utils/lsyscache.h (2)

19-20: LGTM! Include directive properly placed.

The addition of array.h is necessary for the ArrayType return type used in the new functions.


128-130: LGTM! Well-structured function declarations.

The new functions for handling real types are properly placed and follow consistent naming patterns. They enhance PostgreSQL's type system capabilities, particularly important for package support.

Let's verify the usage of these new functions:

✅ Verification successful

Functions are well integrated and used appropriately across the codebase

The verification shows these functions are properly integrated and used across multiple critical components:

  • Parser (parse_func.c): Type resolution during function parsing
  • Function commands (functioncmds.c): Function creation and modification
  • Optimizer (clauses.c): Query optimization and type checking
  • PL/SQL compiler (pl_comp.c): Procedural language compilation
  • Fast path execution (fastpath.c): Function execution optimization

The functions follow consistent usage patterns for handling real types and are used in appropriate contexts for type resolution and validation.

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Check for function usage across the codebase
rg "get_func_real_rettype|repl_func_real_argtype|get_func_real_allargtype" -A 2

Length of output: 5991

src/oracle_test/modules/plsample/plsample.c (1)

173-173: Verify package function return type resolution

The change to use get_func_real_rettype() is appropriate for better return type resolution, especially in the context of package functions. However, we should verify that this function correctly handles package function return types.

✅ Verification successful

Let me analyze the results and generate one more verification script to check package-related handling in the function implementation.


Package function return types are properly handled

The implementation of get_func_real_rettype correctly handles package function return types. The function:

  • Extracts the base return type from the function tuple
  • For Oracle compatibility mode, it:
    • Retrieves package-specific type information
    • Looks up package types using LookupPkgTypeByTypename
    • Validates package existence

The change to use this function in plsample.c is appropriate and safe.

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Check if get_func_real_rettype is properly implemented for package functions
# Test: Search for get_func_real_rettype implementation and its package-related logic

# Look for the implementation
rg -A 10 "get_func_real_rettype"

# Look for package-related return type handling
ast-grep --pattern 'get_func_real_rettype($_) {
  $$$
  if ($_ && $_->pkgoid) {
    $$$
  }
  $$$
}'

Length of output: 16322


Script:

#!/bin/bash
# Look for package-related return type handling in get_func_real_rettype implementation
rg -A 20 "get_func_real_rettype\(HeapTuple proc_tup\)"

Length of output: 2976

src/include/utils/plancache.h (1)

238-239: LGTM: New function declaration for package plan cache invalidation

The declaration of setPlanCacheInvalidForPackage follows proper conventions and integrates well with the existing plan cache infrastructure.

src/include/utils/acl.h (1)

243-245: LGTM: Package ACL function declarations

The new ACL functions for packages follow the established patterns and integrate well with the existing ACL infrastructure.

src/backend/tcop/fastpath.c (1)

160-161: LGTM: Enhanced type resolution for package functions.

The changes correctly handle type resolution for package functions by:

  1. Replacing argument types with their real types
  2. Updating the return type with its real type

This ensures proper type handling when functions are called via the fastpath interface.

src/backend/access/hash/hashvalidate.c (1)

304-305: LGTM: Improved return type validation for hash functions.

The change enhances type validation by using get_func_real_rettype to check the actual return type, which is essential for proper type resolution in the context of packages.

src/include/tcop/cmdtaglist.h (1)

49-49: LGTM: Comprehensive command tag support for packages.

The added command tags properly support the complete lifecycle of packages:

  • Creation: CREATE PACKAGE, CREATE PACKAGE BODY
  • Modification: ALTER PACKAGE
  • Cleanup: DISCARD PACKAGES
  • Removal: DROP PACKAGE, DROP PACKAGE BODY

All tags maintain proper alphabetical ordering and have appropriate flags set:

  • event_trigger_ok: true for DDL operations
  • table_rewrite_ok: false as packages don't involve table rewrites

Also applies to: 105-106, 136-136, 161-162

src/backend/commands/aggregatecmds.c (1)

300-301: LGTM: Variable declaration for parameter type names.

The addition of parametertypeNames aligns with the function signature changes to support package types.

src/backend/commands/seclabel.c (1)

95-96: LGTM: Consistent handling of security labels for package objects.

The addition of OBJECT_PACKAGE and OBJECT_PACKAGE_BODY to the list of objects that don't support security labels is appropriate and follows the established pattern.

src/backend/commands/dropcmds.c (1)

337-351: LGTM: Well-structured implementation of package drop handling.

The implementation correctly:

  1. Checks for schema existence
  2. Provides distinct messages for packages and package bodies
  3. Follows the established pattern for other object types

However, consider adding a verification step to ensure proper cleanup of package-related objects.

✅ Verification successful

Let me try a different search pattern to find package-related cleanup code.


Package drop handling is properly implemented with cleanup

The implementation is well-structured and includes proper cleanup through:

  • DropPackageById() for package deletion
  • DropPackageBodyById() for package body deletion
  • Package cache cleanup via PackageCacheDelete() and FreePackageCache()
  • Integration with the dependency management system in dependency.c
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify the cleanup of package-related objects
# Test: Search for package-related cleanup code in dependency handling

# Check for package dependency handling
ast-grep --pattern 'case OBJECT_PACKAGE:
  $$$
  break;'

# Check for package body dependency handling
ast-grep --pattern 'case OBJECT_PACKAGE_BODY:
  $$$
  break;'

Length of output: 30890


Script:

#!/bin/bash
# Search for package-related dependency handling and cleanup code
rg -A 5 "RemovePackage|DropPackage|drop.*package" --type c

Length of output: 2901

src/backend/nodes/makefuncs.c (1)

538-540: LGTM: Proper initialization of new package-related fields

The new fields are correctly initialized with safe default values:

  • function_name set to NULL
  • ref_pkgtype set to false
  • pkgoid set to InvalidOid
src/include/executor/execExpr.h (1)

401-401: LGTM: Package OID field added with size constraint maintained

The addition of pkgoid to track package variables is well-placed in the cparam struct. The change maintains the ExprEvalStep's size constraint of 64 bytes as verified by the existing StaticAssertDecl.

src/bin/pg_dump/pg_dump.h (3)

223-232: LGTM: Well-structured package information type

The PkgInfo struct follows the established pattern for objects with ACLs:

  • Inherits from DumpableObject
  • Includes owner information
  • Contains ACL fields for both regular and initial privileges

751-751: LGTM: Consistent function prototype

The getPackages function declaration follows the established pattern of other catalog access functions in the file.


44-44: Verify package dump order dependencies

The placement of DO_PACKAGE between DO_EXTENSION and DO_FUNC in the DumpableObjectType enum affects the dump order. Please verify that packages are dumped after their dependencies (extensions) and before objects that might depend on them (functions).

✅ Verification successful

Let me gather more information about package dependencies and dump order.


Let me gather one more piece of information about package dependencies.


Based on the gathered information, I can now provide the final response:

Placement of DO_PACKAGE in enum is appropriate

The placement of DO_PACKAGE between DO_EXTENSION and DO_FUNC in the DumpableObjectType enum is correct because:

  • Packages are properly initialized with their namespace dependencies
  • The dump order is managed by sortDumpableObjects which handles dependency resolution
  • Functions can reference packages, so dumping packages before functions is the right order
  • Package initialization includes proper ACL and ownership information needed by dependent objects
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Check if there are any functions or other objects that reference packages
# This helps verify if the dump order is correct

# Search for references to packages in function definitions
rg -l "PACKAGE" | grep -i "function\|procedure"

# Search for direct dependencies on packages
ast-grep --pattern 'CREATE $_ FUNCTION $_ PACKAGE $_'

Length of output: 143


Script:

#!/bin/bash
# Check for package-related code in pg_dump implementation
rg -A 5 "DO_PACKAGE" src/bin/pg_dump/

# Look for dump order handling
rg -A 10 "sortDumpableObjects" src/bin/pg_dump/

# Check for package dependency handling
rg -A 5 "addDumpableDependency|getDumpableDependency" src/bin/pg_dump/

Length of output: 5264


Script:

#!/bin/bash
# Check for package dependency handling in the implementation
rg -A 10 "dumpPackage|getPackages" src/bin/pg_dump/pg_dump.c

# Look for dependency setup in package initialization
rg -B 5 -A 10 "pkginfo\[i\].dobj.objType = DO_PACKAGE" src/bin/pg_dump/pg_dump.c

Length of output: 2532

src/bin/pg_dump/dumputils.c (1)

474-476: LGTM! Verify package ACL handling

The addition of PACKAGE and PACKAGES types to the ACL parsing logic is correct and follows the existing pattern.

Run the following script to verify that all package-related ACL items are handled consistently:

✅ Verification successful

LGTM! Package ACL handling is consistent across the codebase

The verification confirms that package ACL handling is properly implemented:

  • Package-specific ACL constants are defined (ACL_ALL_RIGHTS_PACKAGE)
  • Package privileges are consistently handled in ACL-related functions
  • Default ACL support for packages is implemented (DEFACLOBJ_PACKAGE)
  • Package privilege checks are properly integrated (pg_package_aclcheck, pg_package_aclmask)
  • The changes in dumputils.c align with the overall ACL implementation for packages
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify that package ACLs are handled consistently across the codebase
# Test: Search for other ACL-related code that might need similar package support

# Check for any ACL-related functions that might need package support
rg -A 5 "case.*when.*type.*=.*'FUNCTION'" 

# Check for any direct package privilege checks
rg -A 5 "(PACKAGE|PACKAGES).*privilege"

Length of output: 91


Script:

#!/bin/bash
# Let's try a broader search for ACL-related code patterns

# Search for ACL parsing and privilege-related code
rg -i "acl.*package" -A 5

# Search for type comparisons in ACL context
rg "strcmp.*type.*FUNCTION" -A 5

# Look for privilege-related code mentioning packages
rg -i "privilege.*package" -A 5

# Search for package-related definitions or constants
rg "define.*PACKAGE" -A 2

Length of output: 24187

contrib/ivorysql_ora/src/sysview/sysview--1.0.sql (1)

1016-1016: LGTM! File ends with a newline

The addition of a newline at the end of the file follows good file formatting practices.

src/backend/catalog/pg_aggregate.c (1)

643-646: LGTM! Verify parameter handling in ProcedureCreate

The addition of new parameters to ProcedureCreate is consistent with the implementation pattern.

Run the following script to verify the parameter handling:

✅ Verification successful

LGTM! Parameters are handled correctly in ProcedureCreate

The new parameters parametertypeNames and rettypeName are properly defined in the ProcedureCreate function signature, and passing NULL values for these optional parameters in AggregateCreate is consistent with the function's design. The function accepts NULL values for several array-type parameters as documented in the function header comment.

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify that the new parameters are handled consistently
# Test: Search for other ProcedureCreate calls to ensure consistent parameter usage

# Check all ProcedureCreate calls
ast-grep --pattern 'ProcedureCreate($$$)'

# Check for any related error handling
rg -A 5 "ProcedureCreate.*NULL"

Length of output: 66098


Script:

#!/bin/bash
# Search for ProcedureCreate function calls and their parameters
rg -A 5 "ProcedureCreate\(" src/backend/catalog/

# Search for ProcedureCreate function definition to understand parameter handling
rg -B 5 -A 10 "^ProcedureCreate" src/backend/catalog/

Length of output: 1825


Script:

#!/bin/bash
# Get more context around the ProcedureCreate function definition to see all parameters
rg -B 10 -A 30 "^ProcedureCreate" src/backend/catalog/pg_proc.c

# Get the specific commit that introduced these changes
git log -p src/backend/catalog/pg_aggregate.c | grep -A 10 "ProcedureCreate.*NULL"

Length of output: 1170

src/bin/pg_dump/common.c (2)

42-42: LGTM: Variable declaration follows established pattern

The static variable declaration follows the same pattern as other count variables in the file.


146-147: LGTM: Package collection properly integrated

The package collection is correctly integrated into the schema data collection sequence with appropriate logging.

src/include/oracle_parser/ora_kwlist.h (1)

73-73: LGTM: Keywords properly added for package support

The new keywords "body", "packages", and "specification" are:

  • Correctly categorized as UNRESERVED_KEYWORD with BARE_LABEL
  • Properly placed in alphabetical order
  • Appropriately chosen for package-related syntax

Also applies to: 376-376, 478-478

src/bin/pg_dump/pg_dump_sort.c (1)

64-64: LGTM: Package priority correctly positioned

The PRIO_PACKAGE priority is appropriately placed after PRIO_CAST and before PRIO_FUNC, ensuring packages are created before their contained functions.

src/backend/commands/opclasscmds.c (3)

1207-1214: LGTM! Good improvement in type checking.

Using get_func_real_rettype() instead of directly accessing procform->prorettype is a better approach as it properly handles domain types by returning their base types.


Line range hint 1235-1241: LGTM! Proper type validation for operator class options parsing functions.

The type checking for operator class options parsing functions is correct, ensuring they:

  1. Return void
  2. Take exactly one argument of type internal

Line range hint 1261-1265: LGTM! Comprehensive type validation for various operator class functions.

The type checking is thorough and covers all operator class function types:

  • btree comparison functions (must return int4)
  • btree sort support functions (must return void)
  • btree in_range functions (must return bool)
  • btree equal image functions (must return bool)
  • hash functions (must return int4/int8)

Also applies to: 1282-1286, 1297-1301, 1317-1321, 1344-1348, 1355-1359

src/backend/commands/event_trigger.c (1)

2143-2146: LGTM! Proper support for package-related object types in GRANT commands.

The addition of OBJECT_PACKAGE and OBJECT_PACKAGE_BODY is correct and consistent with Oracle's PL/SQL package support.

src/backend/nodes/nodeFuncs.c (1)

25-25: LGTM! Package cache header inclusion is appropriate.

The addition of packagecache.h is correctly placed with other utility includes and is necessary for the new package-related functionality.

src/bin/pg_dump/pg_backup_archiver.c (2)

Line range hint 853-856: LGTM: Package ACL support added correctly

The package ACL support is properly integrated into the default ACL handling framework, following the same pattern used for other object types.


Line range hint 954-956: LGTM: Package support added to SQL interface

Package support is correctly added to the SQL-accessible version of acldefault(), maintaining consistency with other object types.

src/bin/psql/command.c (1)

887-889: LGTM! Verify describePackages implementation.

The implementation of the \k command for describing packages follows the established pattern used for other similar commands. The code structure and function call pattern are consistent.

Let's verify the implementation of the describePackages function:

✅ Verification successful

Let me try a different approach to find the describePackages function using ripgrep.


Let me get the complete implementation of the describePackages function to verify it thoroughly.


Let me try one more approach to get the function implementation.


Implementation of describePackages function is well-structured and consistent

The implementation follows PostgreSQL's established patterns for describing database objects:

  • Uses proper schema qualification with pg_catalog
  • Handles system objects visibility through showSystem parameter
  • Implements verbose mode with additional columns
  • Follows security best practices with proper SQL pattern validation
  • Provides clear error messages and formatted output
  • Properly manages memory with PQExpBuffer
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify the implementation of describePackages function
# Test: Search for the function definition
ast-grep --pattern 'bool describePackages($pattern, $verbose, $showSystem) {
  $$$
}'

Length of output: 1533


Script:

#!/bin/bash
# Search for describePackages function definition
rg -n "describePackages" --type c

# If found, get the context of the function
rg -n "describePackages" --type c -B 5 -A 15

Length of output: 3739


Script:

#!/bin/bash
# Get the complete implementation of describePackages function
rg -U "bool\s+describePackages.*?^}" --multiline --type c -A 50

Length of output: 65


Script:

#!/bin/bash
# Get the content of describe.c file around the describePackages function
rg -n "describePackages" src/bin/psql/describe.c -B 5 -A 100

Length of output: 3349

src/bin/psql/describe.c (2)

3790-3796: LGTM!

The variable declarations follow the standard pattern used in other similar functions in this file.


3797-3858: ⚠️ Potential issue

Verify SQL query compatibility with older PostgreSQL versions.

The SQL query uses features like LEFT JOIN that need to be verified for compatibility with older PostgreSQL versions supported by this code.

Run this script to check version compatibility:

Additionally, consider adding version checks similar to other functions in this file:

+if (pset.sversion < 140000)
+{
+    char sverbuf[32];
+    pg_log_error("The server (version %s) does not support PL/SQL packages.",
+                 formatPGVersionNumber(pset.sversion, false,
+                                     sverbuf, sizeof(sverbuf)));
+    return true;
+}
src/bin/psql/tab-complete.c (4)

646-658: LGTM! Well-structured package completion query implementation.

The SchemaQuery array for packages follows the established pattern and includes proper version checking. The implementation correctly handles quoting of package names and gracefully falls back for older server versions.


1256-1256: LGTM! Appropriate additions to CREATE command options.

The additions of EDITIONABLE, NONEDITIONABLE and PACKAGE to the CREATE command completion options are consistent with the Oracle compatibility features.

Also applies to: 1267-1267, 1272-1272


2828-2828: LGTM! Added PACKAGE to COMMENT ON options.

The addition of PACKAGE to the COMMENT ON command completion options is appropriate and consistent with other object types.


4081-4081: LGTM! Comprehensive updates to privilege-related completions.

The changes properly integrate packages into:

  • ALTER DEFAULT PRIVILEGES options
  • GRANT/REVOKE completion paths
  • Help command completion

Also applies to: 4109-4109, 4135-4136

configure (1)

838-838: LGTM!

The placement of enable_cursor_unname variable is appropriate in the configuration variables section.

Comment thread src/bin/pg_dump/pg_dump.c
Comment on lines +12225 to +12345
/*
* dump a package
*/
static void
dumpPackage(Archive *fout, const PkgInfo *pkginfo)
{
DumpOptions *dopt = fout->dopt;
PQExpBuffer query;
PQExpBuffer q;
PQExpBuffer delqry;
PQExpBuffer pkgname;
PQExpBuffer asPart;
PGresult *res;
char *package_head;
char *body_src;
char *pkgsrc;
PQExpBuffer package_identifier;
/* Skip if not to be dumped */
if (!pkginfo->dobj.dump || dopt->dataOnly)
return;
query = createPQExpBuffer();
q = createPQExpBuffer();
delqry = createPQExpBuffer();
pkgname = createPQExpBuffer();
asPart = createPQExpBuffer();
package_identifier = createPQExpBuffer();
appendPQExpBuffer(query,
"SELECT pkgsrc,"
"pg_catalog.pg_get_package_head(p.oid) AS package_head, "
" (select bodysrc from pg_package_body WHERE pkgoid = p.oid) as bodysrc "
"FROM pg_package p "
"WHERE p.oid = '%u'::pg_catalog.oid",
pkginfo->dobj.catId.oid);
res = ExecuteSqlQueryForSingleRow(fout, query->data);
package_head = PQgetvalue(res, 0, PQfnumber(res, "package_head"));
body_src = PQgetvalue(res, 0, PQfnumber(res, "bodysrc"));
pkgsrc = PQgetvalue(res, 0, PQfnumber(res, "pkgsrc"));
appendPQExpBuffer(package_identifier, "%s.",
fmtId(pkginfo->dobj.namespace->dobj.name));
/* add quote */
appendPQExpBuffer(pkgname, "%s",
fmtId(pkginfo->dobj.name));
appendPQExpBuffer(package_identifier, "%s",
pkgname->data);
appendPQExpBuffer(delqry, "DROP PACKAGE %s;\n",
package_identifier->data);
appendPQExpBuffer(asPart, " AS\n");
if (dopt->disable_dollar_quoting)
appendStringLiteralAH(asPart, pkgsrc, fout);
else
appendStringLiteralDQ(asPart, pkgsrc, NULL);
/* append create or replace package */
appendPQExpBuffer(q, "%s %s;\n",
package_head,
asPart->data);
/* add slash to terminate */
if (((ArchiveHandle *) fout)->format == archNull &&
db_mode == DB_ORACLE)
appendPQExpBufferStr(q, "/\n");
if (body_src != NULL && body_src[0] != '\0')
{
PQExpBuffer bodyasPart;
bodyasPart = createPQExpBuffer();
appendPQExpBuffer(bodyasPart, " AS ");
if (dopt->disable_dollar_quoting)
appendStringLiteralAH(bodyasPart, body_src, fout);
else
appendStringLiteralDQ(bodyasPart, body_src, NULL);
/*
* pakcage name and schema name should add quote
*/
appendPQExpBuffer(q, "CREATE PACKAGE BODY %s %s;\n",
package_identifier->data,
bodyasPart->data);
/* add slash to terminate */
if (((ArchiveHandle *) fout)->format == archNull &&
db_mode == DB_ORACLE)
appendPQExpBufferStr(q, "/\n");
destroyPQExpBuffer(bodyasPart);
}
append_depends_on_extension(fout, q, &pkginfo->dobj,
"pg_catalog.pg_package", "PACKAGE",
package_identifier->data);
if (dopt->binary_upgrade)
binary_upgrade_extension_member(q, &pkginfo->dobj,
"PACKAGE", pkgname->data,
pkginfo->dobj.namespace->dobj.name);
if (pkginfo->dobj.dump & DUMP_COMPONENT_DEFINITION)
ArchiveEntry(fout, pkginfo->dobj.catId, pkginfo->dobj.dumpId,
ARCHIVE_OPTS(.tag = pkgname->data,
.namespace = pkginfo->dobj.namespace->dobj.name,
.owner = pkginfo->rolname,
.description = "PACKAGE",
.section = SECTION_PRE_DATA,
.createStmt = q->data,
.dropStmt = delqry->data));
/*
* we only dump package comment, because oracle doesn't
* support comment statment on package and its body
*/
if (pkginfo->dobj.dump & DUMP_COMPONENT_COMMENT)
dumpComment(fout, "PACKAGE", pkgname->data,
pkginfo->dobj.namespace->dobj.name, pkginfo->rolname,
pkginfo->dobj.catId, 0, pkginfo->dobj.dumpId);
if (pkginfo->dobj.dump & DUMP_COMPONENT_SECLABEL)
dumpSecLabel(fout, "PACKAGE", pkgname->data,
pkginfo->dobj.namespace->dobj.name, pkginfo->rolname,
pkginfo->dobj.catId, 0, pkginfo->dobj.dumpId);
if (pkginfo->dobj.dump & DUMP_COMPONENT_ACL)
dumpACL(fout, pkginfo->dobj.dumpId, InvalidDumpId, "PACKAGE",
pkgname->data, NULL,
pkginfo->dobj.namespace->dobj.name,
NULL, pkginfo->rolname, &(pkginfo->dacl));
PQclear(res);
destroyPQExpBuffer(query);
destroyPQExpBuffer(q);
destroyPQExpBuffer(delqry);
destroyPQExpBuffer(pkgname);
destroyPQExpBuffer(asPart);
destroyPQExpBuffer(package_identifier);
}
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue

Multiple issues in package dump implementation

  1. SQL Injection vulnerability in query construction:
appendPQExpBuffer(query,
        "SELECT pkgsrc,"
        "pg_catalog.pg_get_package_head(p.oid) AS package_head, "
        " (select bodysrc from pg_package_body WHERE pkgoid = p.oid) as bodysrc "
        "FROM pg_package p "
        "WHERE p.oid = '%u'::pg_catalog.oid",
        pkginfo->dobj.catId.oid);
  1. Typo in comment at line 12294: "pakcage" should be "package"

  2. Inconsistent error handling - some PQExpBuffer operations aren't checked for failure

Suggested fixes:

  1. Use proper parameter binding:
-        "WHERE p.oid = '%u'::pg_catalog.oid",
+        "WHERE p.oid = $1::pg_catalog.oid",
  1. Add error handling:
+ if (PQExpBufferBroken(query) || PQExpBufferBroken(q) || 
+     PQExpBufferBroken(delqry) || PQExpBufferBroken(pkgname) ||
+     PQExpBufferBroken(asPart) || PQExpBufferBroken(package_identifier))
+    exit_horribly(NULL, "out of memory\n");

Comment thread src/bin/pg_dump/pg_dump.c
Comment on lines +6700 to +6775
/*
* getPackages:
* read all the user-defined package in the system catalogs and
* return them in the PkgInfo* structure
*
* numPkgs is set to the number of packages read in
*/
PkgInfo *
getPackages(Archive *fout, int *numPkgs)
{
PGresult *res;
int ntups;
int i;
PQExpBuffer query = createPQExpBuffer();
PkgInfo *pkginfo;
int i_tableoid;
int i_pkgname;
int i_oid;
int i_pkgnamespace;
int i_rolname;
int i_pkgacl;
int i_acldefault;
appendPQExpBuffer(query,
"SELECT p.tableoid, p.pkgname, p.oid, p.pkgnamespace,"
"p.pkgowner,"
"p.pkgacl,"
"acldefault('P', p.pkgowner) AS acldefault "
"FROM pg_package p "
"LEFT JOIN pg_init_privs pip ON "
"(p.oid = pip.objoid "
"AND pip.classoid = 'pg_package'::regclass "
"AND pip.objsubid = 0) "
" where p.pkgnamespace != "
"(SELECT oid FROM pg_namespace "
"WHERE nspname = 'pg_catalog')"
);
res = ExecuteSqlQuery(fout, query->data, PGRES_TUPLES_OK);
ntups = PQntuples(res);
*numPkgs = ntups;
pkginfo = (PkgInfo *) pg_malloc0(ntups * sizeof(PkgInfo));
i_tableoid = PQfnumber(res, "tableoid");
i_pkgname = PQfnumber(res, "pkgname");
i_oid = PQfnumber(res, "oid");
i_pkgnamespace = PQfnumber(res, "pkgnamespace");
i_rolname = PQfnumber(res, "rolname");
i_pkgacl = PQfnumber(res, "pkgacl");
i_acldefault = PQfnumber(res, "acldefault");

for (i = 0; i < ntups; i++)
{
pkginfo[i].dobj.objType = DO_PACKAGE;
pkginfo[i].dobj.catId.tableoid = atooid(PQgetvalue(res, i, i_tableoid));
pkginfo[i].dobj.catId.oid = atooid(PQgetvalue(res, i, i_oid));
AssignDumpId(&pkginfo[i].dobj);
pkginfo[i].dobj.name = pg_strdup(PQgetvalue(res, i, i_pkgname));
pkginfo[i].dobj.namespace =
findNamespace(atooid(PQgetvalue(res, i, i_pkgnamespace)));
pkginfo[i].rolname = pg_strdup(PQgetvalue(res, i, i_rolname));
pkginfo[i].pkgacl = pg_strdup(PQgetvalue(res, i, i_pkgacl));
pkginfo[i].dacl.acldefault = pg_strdup(PQgetvalue(res, i, i_acldefault));
pkginfo[i].dacl.privtype = 0;
pkginfo[i].dacl.initprivs = NULL;

/* Decide whether we want to dump it */
selectDumpableObject(&(pkginfo[i].dobj), fout);
/* Do not try to dump ACL if no ACL exists. */
if (!PQgetisnull(res, i, i_pkgacl))
pkginfo[i].dobj.dump &= ~DUMP_COMPONENT_ACL;
if (strlen(pkginfo[i].rolname) == 0)
pg_log_warning("WARNING: owner of package \"%s\" appears to be invalid\n",
pkginfo[i].dobj.name);
}
PQclear(res);
destroyPQExpBuffer(query);
return pkginfo;
}
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue

Critical issues in package information retrieval implementation

Several issues need to be addressed:

  1. The SQL query references 'rolname' column (line 6744) but it's not included in the SELECT clause (lines 6723-6726).
  2. No error handling for memory allocation at line 6739.
  3. Potential memory leak if early return after memory allocation.

Suggested fixes:

 appendPQExpBuffer(query,
-                    "SELECT p.tableoid, p.pkgname, p.oid, p.pkgnamespace,"
-                    "p.pkgowner,"
+                    "SELECT p.tableoid, p.pkgname, p.oid, p.pkgnamespace, "
+                    "p.pkgowner, pg_catalog.pg_get_userbyid(p.pkgowner) as rolname, "
                     "p.pkgacl,"
                     "acldefault('P', p.pkgowner) AS acldefault "

Add error handling:

+ if (!pkginfo)
+    exit_horribly(NULL, "out of memory\n");

Committable suggestion skipped: line range outside the PR's diff.

Comment on lines +10044 to +10059
CreatePackageBodyStmt:
CREATE opt_or_replace opt_ora_editioned PACKAGE_BODY BODY package_names
opt_ora_sharing_clause package_body_is_or_as package_src
{
CreatePackageBodyStmt *n = makeNode(CreatePackageBodyStmt);
n->replace = $2;
n->editable = $3;
n->pkgname = $6;
n->bodysrc = $9;
$$ = (Node *)n;
}
;
package_body_is_or_as:
IS { set_oracle_plsql_body(yyscanner, OraBody_PACKAGEBODY); }
|AS { set_oracle_plsql_body(yyscanner, OraBody_PACKAGEBODY); }
;
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🛠️ Refactor suggestion

Consider package specification dependency validation

The package body grammar is well-structured, but consider adding validation to ensure:

  1. The referenced package specification exists
  2. The body's interface matches the specification
  3. Dependencies are tracked for proper invalidation

Comment on lines +213 to +215
static void record_plan_internel_function_dependency(PlannerInfo *root,
FuncExpr *funcexpr);

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🛠️ Refactor suggestion

Correct the misspelling of "internal" in function name

The function name record_plan_internel_function_dependency is misspelled. The word "internel" should be "internal". This occurs in the function prototype, its definition, and all references to it.

Apply the following diffs to correct the spelling throughout the code:

@@ -213,7 +213,7 @@
 
-static void record_plan_internel_function_dependency(PlannerInfo *root,
+static void record_plan_internal_function_dependency(PlannerInfo *root,
 											FuncExpr *funcexpr);
@@ -1985,6 +1985,6 @@
 	if (FUNC_EXPR_FROM_PG_PROC(((FuncExpr *) node)->function_from))
 		record_plan_function_dependency(root,
 									((FuncExpr *) node)->funcid);
 	else
-		record_plan_internel_function_dependency(root,
+		record_plan_internal_function_dependency(root,
 									(FuncExpr *) node);
@@ -3455,6 +3455,6 @@

 /*
  * record package or subproc function
  * dependency
  */
-static void
-record_plan_internel_function_dependency(PlannerInfo *root,
+static void
+record_plan_internal_function_dependency(PlannerInfo *root,
 										FuncExpr *funcexpr)
 {

Additionally, correct the spelling and grammar in comments within the function definition:

 	Assert(funcexpr->function_from != FUNC_FROM_PG_PROC);

 	/*
-	 * there, we only support package or inline function
-	 * others, we ignore it
+	 * Here, we only support package or inline functions;
+	 * others are ignored.
 	 */
 	if (funcexpr->function_from == FUNC_FROM_PACKAGE ||
 		funcexpr->function_from == FUNC_FROM_SUBPROCFUNC)
 	{
 		/* use top function to get some informations */
+		/* Use the top function to get some information */
 		func_id = get_top_function_info(funcexpr,
 							&record_package);

Also applies to: 1985-1990, 3455-3497

* File:pg_package_body.h
*
* Abstract:
* Definitions for the PLISQL Package Body
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue

Correct terminology: Replace 'PLISQL' with 'PL/pgSQL'

The term 'PLISQL' should be updated to 'PL/pgSQL' to reflect the correct naming convention for PostgreSQL's procedural language.

Apply this diff:

- *      Definitions for the PLISQL Package Body
+ *      Definitions for the PL/pgSQL Package Body
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
* Definitions for the PLISQL Package Body
* Definitions for the PL/pgSQL Package Body

Comment on lines +2230 to +2355
static void
ExecGrant_Package(InternalGrant *istmt)
{
Relation relation;
ListCell *cell;

if (istmt->all_privs && istmt->privileges == ACL_NO_RIGHTS)
istmt->privileges = ACL_ALL_RIGHTS_PACKAGE;

relation = table_open(PackageRelationId, RowExclusiveLock);

foreach(cell, istmt->objects)
{
Oid pkgId = lfirst_oid(cell);
Form_pg_package pg_package_tuple;
Datum aclDatum;
bool isNull;
AclMode avail_goptions;
AclMode this_privileges;
Acl *old_acl;
Acl *new_acl;
Oid grantorId;
Oid ownerId;
HeapTuple tuple;
HeapTuple newtuple;
Datum values[Natts_pg_package];
bool nulls[Natts_pg_package];
bool replaces[Natts_pg_package];
int noldmembers;
int nnewmembers;
Oid *oldmembers;
Oid *newmembers;

tuple = SearchSysCache1(PKGOID, ObjectIdGetDatum(pkgId));
if (!HeapTupleIsValid(tuple))
elog(ERROR, "cache lookup failed for package %u", pkgId);

pg_package_tuple = (Form_pg_package) GETSTRUCT(tuple);

/*
* Get owner ID and working copy of existing ACL. If there's no ACL,
* substitute the proper default.
*/
ownerId = pg_package_tuple->pkgowner;
aclDatum = SysCacheGetAttr(PKGOID, tuple, Anum_pg_package_pkgacl,
&isNull);
if (isNull)
{
old_acl = acldefault(OBJECT_PACKAGE, ownerId);
/* There are no old member roles according to the catalogs */
noldmembers = 0;
oldmembers = NULL;
}
else
{
old_acl = DatumGetAclPCopy(aclDatum);
/* Get the roles mentioned in the existing ACL */
noldmembers = aclmembers(old_acl, &oldmembers);
}

/* Determine ID to do the grant as, and package grant options */
select_best_grantor(GetUserId(), istmt->privileges,
old_acl, ownerId,
&grantorId, &avail_goptions);

/*
* Restrict the privileges to what we can actually grant, and emit the
* standards-mandated warning and error messages.
*/
this_privileges =
restrict_and_check_grant(istmt->is_grant, avail_goptions,
istmt->all_privs, istmt->privileges,
pkgId, grantorId, OBJECT_PACKAGE,
NameStr(pg_package_tuple->pkgname),
0, NULL);

/*
* Generate new ACL.
*/
new_acl = merge_acl_with_grant(old_acl, istmt->is_grant,
istmt->grant_option, istmt->behavior,
istmt->grantees, this_privileges,
grantorId, ownerId);

/*
* We need the members of both old and new ACLs so we can correct the
* shared dependency information.
*/
nnewmembers = aclmembers(new_acl, &newmembers);

/* finished building new ACL value, now insert it */
MemSet(values, 0, sizeof(values));
MemSet(nulls, false, sizeof(nulls));
MemSet(replaces, false, sizeof(replaces));

replaces[Anum_pg_package_pkgacl - 1] = true;
values[Anum_pg_package_pkgacl - 1] = PointerGetDatum(new_acl);

newtuple = heap_modify_tuple(tuple, RelationGetDescr(relation), values,
nulls, replaces);

CatalogTupleUpdate(relation, &newtuple->t_self, newtuple);

FreePackageCache(&pkgId);

/* Update initial privileges for extensions */
recordExtensionInitPriv(pkgId, PackageRelationId, 0, new_acl);

/* Update the shared dependency ACL info */
updateAclDependencies(PackageRelationId, pkgId, 0,
ownerId,
noldmembers, oldmembers,
nnewmembers, newmembers);

ReleaseSysCache(tuple);

pfree(new_acl);

/* prevent error when processing duplicate objects */
CommandCounterIncrement();
}

table_close(relation, RowExclusiveLock);

}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codebase verification

⚠️ Potential issue

Function parameter type mismatch in FreePackageCache call

The FreePackageCache function expects a PackageCacheKey* parameter as shown in its declaration in src/include/utils/packagecache.h, but it's being called with &pkgId where pkgId is an Oid. This is a type mismatch that needs to be corrected.

  • src/backend/catalog/aclchk.c: The call FreePackageCache(&pkgId) needs to be updated to use the correct parameter type.

Note: The review comment's suggested fix was incorrect as it assumed the function accepts an Oid parameter. The actual fix would need to properly construct a PackageCacheKey structure before passing it to FreePackageCache.

🔗 Analysis chain

Verify the usage of FreePackageCache with correct argument type.

In the ExecGrant_Package function, the FreePackageCache function is called with &pkgId. Ensure that FreePackageCache expects a pointer to Oid. If it expects an Oid value, remove the address-of operator.

Apply this diff to correct the function call if necessary:

-    		FreePackageCache(&pkgId);
+    		FreePackageCache(pkgId);

Run the following script to confirm the expected parameter type of FreePackageCache:

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Check the definition of FreePackageCache to verify its parameter type.

# Search for the function definition of FreePackageCache
rg 'void\s+FreePackageCache\s*\(\s*Oid\s+\w+\s*\)' --files-with-matches src/

Length of output: 78


Script:

#!/bin/bash
# Let's try different search patterns to find the FreePackageCache function definition

# Search for FreePackageCache with any parameter type
rg "FreePackageCache\s*\(" -A 3

# Also search for its prototype/declaration
rg "FreePackageCache" --type h

# Search using ast-grep for function definition
ast-grep --pattern 'void FreePackageCache($_) { $$$ }'

Length of output: 3545

Comment on lines +3466 to +3521
accesssource = SysCacheGetAttr(PKGOID, pkgtup,
Anum_pg_package_accesssource,
&isnull);
if (!isnull)
{
char *str;
List *sourcelist;
ListCell *lc;
char *access_tag;

appendStringInfo(&buf, " ACCESSIBLE BY (");

str = TextDatumGetCString(accesssource);
sourcelist = (List *) stringToNode(str);

foreach (lc, sourcelist)
{
AccessorItem *access = (AccessorItem *) lfirst(lc);
char *unitname;

Assert(access->type == T_AccessorItem);

switch (access->unitkind)
{
case ACCESSOR_FUNCTION:
access_tag = "FUNCTION";
break;
case ACCESSOR_PROCEDURE:
access_tag = "PROCEDURE";
break;
case ACCESSOR_PACKAGE:
access_tag = "PACKAGE";
break;
case ACCESSOR_TRIGGER:
access_tag = "TRIGGER";
break;
case ACCESSOR_TYPE:
access_tag = "TYPE";
break;
case ACCESSOR_UNKNOW:
access_tag = " ";
break;
default:
elog(ERROR, "unknown proper type %u", access->unitkind);
break;
}

unitname = NameListToString(access->unitname);
appendStringInfo(&buf, "%s %s,",
access_tag,
unitname);
pfree(unitname);
}
/* replace last ',' to )' */
buf.data[buf.len] = ')';
}
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🛠️ Refactor suggestion

Refactor the ACCESSIBLE BY clause generation for better readability.

The ACCESSIBLE BY clause generation code is quite lengthy and could benefit from some refactoring to improve readability:

  • Extract the switch statement into a separate function to map unitkind to access_tag.
  • Consider using a lookup table instead of the long switch statement.
  • Use a separate function to generate each ACCESSIBLE BY item to reduce nesting.

This will make the code easier to understand and maintain.

extern Oid get_package_namespace(Oid pkgid);
extern Oid get_package_bodyid(Oid pkgoid, bool miss_ok);
extern void check_package_name(Oid nspname, char *newpkgname, char *oldpkgname);
extern void IsTherePackageInNamespace(char *new_name, Oid namespace);
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codebase verification

Based on the code review, I can now provide a final response regarding the error handling documentation for name validation functions:

Document error handling for package name validation functions

The implementation shows that IsTherePackageInNamespace and check_package_name have the following error conditions:

  • IsTherePackageInNamespace: Throws a duplicate function error (ERRCODE_DUPLICATE_FUNCTION) if a package with the same name exists in the target namespace
  • check_package_name: Throws an error if attempting to use the reserved name "standard" outside the SYS namespace

Please add error documentation to the function declarations:

  • check_package_name(Oid nspname, char *newpkgname, char *oldpkgname):

    • Errors if newpkgname is "standard" and nspname is not PG_SYS_NAMESPACE
    • Errors if oldpkgname is "standard"
  • IsTherePackageInNamespace(char *new_name, Oid namespace):

    • Errors with ERRCODE_DUPLICATE_FUNCTION if package exists in namespace
🔗 Analysis chain

Clarify error handling for name validation functions

The naming validation functions should document:

  • Error conditions and types of exceptions thrown
  • Whether they handle schema qualification
  • Naming constraints and restrictions

Also applies to: 41-41

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Search for error handling patterns in name validation
rg "ereport\(ERROR" src/backend/commands/packagecmds.c | grep -E "check_package_name|IsTherePackageInNamespace"

Length of output: 113


Script:

#!/bin/bash
# Let's first check the implementation of IsTherePackageInNamespace
ast-grep --pattern 'void IsTherePackageInNamespace($$$)'

# Also search for any error reporting related to package names
rg -A 3 "IsTherePackageInNamespace|check_package_name" src/backend/commands/packagecmds.c

# Look for any error handling patterns in the package commands
rg -A 3 "ereport\(ERROR.*package" src/backend/commands/packagecmds.c

Length of output: 68483


Script:

#!/bin/bash
# Let's check the implementation file directly
cat src/backend/commands/packagecmds.c

# Also check for any related header files that might contain documentation
cat src/include/commands/packagecmds.h

Length of output: 34260

Comment on lines +37 to +38
scansup.o \
parse_package.o
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codebase verification

Parser integration needs additional components

The parse_package.o addition to the Makefile is incomplete. While parse_package.c is present and implements package parsing functionality, the required grammar rules in gram.y and token definitions in scan.l are missing. These are essential components for proper SQL package parsing support.

  • Add package-related token definitions to src/backend/parser/scan.l
  • Add package grammar rules to src/backend/parser/gram.y
  • Ensure these changes are synchronized with the functionality in parse_package.c
🔗 Analysis chain

LGTM: Verify parser integration completeness

The addition of parse_package.o is correct. However, let's verify the complete parser integration.

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Check for grammar updates for package support
rg -l "package" src/backend/parser/gram.y

# Verify scanner updates for package keywords
rg -l "package" src/backend/parser/scan.l

Length of output: 83


Script:

#!/bin/bash
# Let's check if the grammar and scanner files exist first
fd "gram.y|scan.l" src/backend/parser/

# Then let's check for any package-related files in parser directory
fd "package" src/backend/parser/

# Look for package-related patterns in all parser files
rg -l "PACKAGE|Package" src/backend/parser/

Length of output: 273


Script:

#!/bin/bash
# Let's examine the grammar file for package-related rules
rg -A 5 -B 5 "package" src/backend/parser/gram.y

# Check scanner for package-related tokens
rg -A 2 -B 2 "package" src/backend/parser/scan.l

# Look at the package parser implementation
head -n 50 src/backend/parser/parse_package.c

Length of output: 1840

Comment on lines +321 to +325
&requiredResultType,
&parametertypeNames);
if (parametertypeNames != NULL)
elog(ERROR, "aggreate function doesn't support package'type as argtype");

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue

Validate the error message for package type restriction.

The error message has a typo ("aggreate" instead of "aggregate") and could be more descriptive.

Apply this diff to fix the typo and improve the error message:

-			elog(ERROR, "aggreate function doesn't support package'type as argtype");
+			elog(ERROR, "aggregate functions do not support package types as argument types");
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
&requiredResultType,
&parametertypeNames);
if (parametertypeNames != NULL)
elog(ERROR, "aggreate function doesn't support package'type as argtype");
&requiredResultType,
&parametertypeNames);
if (parametertypeNames != NULL)
elog(ERROR, "aggregate functions do not support package types as argument types");

@bigplaice bigplaice reopened this Dec 6, 2024
@gaoxueyu gaoxueyu merged commit e623b61 into IvorySQL:master Dec 6, 2024
This was referenced Nov 4, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants