Skip to content

feat(UTL_RAW): UTL_RAW.CAST_TO_RAW#1337

Open
hs-liuxh wants to merge 2 commits into
IvorySQL:masterfrom
hs-liuxh:ora/utl_raw
Open

feat(UTL_RAW): UTL_RAW.CAST_TO_RAW#1337
hs-liuxh wants to merge 2 commits into
IvorySQL:masterfrom
hs-liuxh:ora/utl_raw

Conversation

@hs-liuxh
Copy link
Copy Markdown
Collaborator

@hs-liuxh hs-liuxh commented May 15, 2026

Oracle compatible feature: UTL_RAW

#1057

Summary by CodeRabbit

  • New Features
    • Added an Oracle-compatible UTL_RAW package exposing CAST_TO_RAW and endian constants for converting text to hexadecimal.
  • Tests
    • Added regression tests and expected outputs verifying CAST_TO_RAW behavior for normal, empty, NULL, multibyte, mixed, and special-character inputs; included the suite in install-time checks.

Review Change Stack

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented May 15, 2026

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: e066fb74-7813-4e7a-89ec-661ba6d0465c

📥 Commits

Reviewing files that changed from the base of the PR and between 4822d52 and 55f4796.

📒 Files selected for processing (2)
  • contrib/ivorysql_ora/meson.build
  • contrib/ivorysql_ora/src/builtin_packages/utl_raw/utl_raw.c
✅ Files skipped from review due to trivial changes (1)
  • contrib/ivorysql_ora/meson.build

📝 Walkthrough

Walkthrough

Adds an Oracle-compatible UTL_RAW package: a C function converting text to uppercase hex, a SQL package/spec exposing CAST_TO_RAW and endianness constants, build/meson wiring, and a regression test suite with expected outputs.

Changes

UTL_RAW Oracle-Compatible Package

Layer / File(s) Summary
C hex conversion function
contrib/ivorysql_ora/src/builtin_packages/utl_raw/utl_raw.c
ora_utl_raw_cast_to_raw converts input text bytes to uppercase hexadecimal into a varlena text result.
SQL package specification and wrapper
contrib/ivorysql_ora/src/builtin_packages/utl_raw/utl_raw--1.0.sql
Adds sys.utl_raw_cast_to_raw(c text) (C-backed, STRICT, IMMUTABLE) and UTL_RAW package with CAST_TO_RAW and endianness constants; package body forwards to helper.
Build integration and test suite
contrib/ivorysql_ora/Makefile, contrib/ivorysql_ora/meson.build, contrib/ivorysql_ora/ivorysql_ora_merge_sqls, contrib/ivorysql_ora/sql/utl_raw.sql, contrib/ivorysql_ora/expected/utl_raw.out
Makefile/meson add utl_raw source and object and register regression target; merge list includes SQL module; SQL tests exercise CAST_TO_RAW for normal, NULL, empty, multibyte/mixed, and special-character inputs with expected output.

Sequence Diagram

sequenceDiagram
  participant Test as Test SQL
  participant Pkg as UTL_RAW.CAST_TO_RAW
  participant Helper as sys.utl_raw_cast_to_raw
  participant CFunc as ora_utl_raw_cast_to_raw
  Test->>Pkg: CAST_TO_RAW(varchar2)
  Pkg->>Helper: forward (cast to text)
  Helper->>CFunc: call C function
  CFunc->>Helper: return hex text
  Helper->>Pkg: return varchar2 result
  Pkg->>Test: return result
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

Suggested reviewers

  • bigplaice
  • jiaoshuntian

Poem

I hop through bytes both small and vast,
Turning each nibble bright and fast,
From C to SQL I carry the lore,
Hex shines like carrots—now CAST_TO_RAW galore! 🐰

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly and specifically summarizes the main change: implementing UTL_RAW.CAST_TO_RAW functionality, which aligns directly with the PR objectives and the majority of changes.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Warning

There were issues while running some tools. Please review the errors and either fix the tool's configuration or disable the tool if it's a critical failure.

🔧 OpenGrep (1.20.0)

OpenGrep fatal error (exit code 2): [00.14][ERROR]: Error: exception Unix_error: No such file or directory stat contrib/ivorysql_ora/src/builtin_packages/utl_raw/utl_raw.c
Raised by primitive operation at UTmp.replace_named_pipe_by_regular_file_if_needed in file "libs/commons/UTmp.ml", line 145, characters 8-27
Called from Scan_CLI.replace_target_roots_by_regular_files_where_needed.(fun) in file "src/osemgrep/cli_scan/Scan_CLI.ml", lines 1086-1087, characters 19-65
Called from List_.fast_map in file "libs/commons/List_.ml", line 8


Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

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: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@contrib/ivorysql_ora/src/builtin_packages/utl_raw/utl_raw.c`:
- Around line 45-48: Before calling palloc to allocate result, check that the
computed size (VARHDRSZ + datalen * 2) does not exceed MaxAllocSize (or
otherwise allowable allocation threshold) and raise a controlled ereport/elog
error if it does; specifically, in the code that computes datalen and assigns
result (using VARHDRSZ, datalen, and palloc), compute the needed_size = VARHDRSZ
+ datalen * 2, verify needed_size <= MaxAllocSize (or use SizeIsValid/alloc size
helper used in the project), and call ereport(ERROR, ...) with a clear message
on overly large input when the check fails, only then call palloc(needed_size)
to assign result.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: aae3b8e1-469c-4f4d-9736-03306cb80cc8

📥 Commits

Reviewing files that changed from the base of the PR and between 35e086c and 4822d52.

📒 Files selected for processing (6)
  • contrib/ivorysql_ora/Makefile
  • contrib/ivorysql_ora/expected/utl_raw.out
  • contrib/ivorysql_ora/ivorysql_ora_merge_sqls
  • contrib/ivorysql_ora/sql/utl_raw.sql
  • contrib/ivorysql_ora/src/builtin_packages/utl_raw/utl_raw--1.0.sql
  • contrib/ivorysql_ora/src/builtin_packages/utl_raw/utl_raw.c

Comment on lines +45 to +48
datalen = VARSIZE_ANY_EXHDR(input);

result = palloc(VARHDRSZ + datalen * 2);
out = VARDATA(result);
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 | 🟡 Minor | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

cat -n contrib/ivorysql_ora/src/builtin_packages/utl_raw/utl_raw.c | head -60

Repository: IvorySQL/IvorySQL

Length of output: 2143


🏁 Script executed:

rg "MaxAllocSize" --type c -B2 -A2

Repository: IvorySQL/IvorySQL

Length of output: 44163


🏁 Script executed:

rg "VARHDRSZ.*datalen" --type c -B3 -A3

Repository: IvorySQL/IvorySQL

Length of output: 3619


🏁 Script executed:

grep -n "if.*datalen.*>" contrib/ivorysql_ora/src/builtin_packages/utl_raw/utl_raw.c

Repository: IvorySQL/IvorySQL

Length of output: 43


🏁 Script executed:

rg "encode\.c" --type c -A5 "MaxAllocSize - VARHDRSZ" | head -20

Repository: IvorySQL/IvorySQL

Length of output: 125


Add an explicit size guard before output allocation.

Line 47 computes VARHDRSZ + datalen * 2 without checking MaxAllocSize. For very large inputs, palloc will fail with a low-level allocation error instead of a controlled function error. PostgreSQL's established practice is to pre-check allocation sizes to provide deterministic, user-friendly error messages.

💡 Suggested fix
 	data = VARDATA_ANY(input);
 	datalen = VARSIZE_ANY_EXHDR(input);
 
+	if (datalen > (MaxAllocSize - VARHDRSZ) / 2)
+		ereport(ERROR,
+				(errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
+				 errmsg("input is too long for UTL_RAW.CAST_TO_RAW")));
+
 	result = palloc(VARHDRSZ + datalen * 2);
 	out = VARDATA(result);
📝 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
datalen = VARSIZE_ANY_EXHDR(input);
result = palloc(VARHDRSZ + datalen * 2);
out = VARDATA(result);
data = VARDATA_ANY(input);
datalen = VARSIZE_ANY_EXHDR(input);
if (datalen > (MaxAllocSize - VARHDRSZ) / 2)
ereport(ERROR,
(errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
errmsg("input is too long for UTL_RAW.CAST_TO_RAW")));
result = palloc(VARHDRSZ + datalen * 2);
out = VARDATA(result);
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@contrib/ivorysql_ora/src/builtin_packages/utl_raw/utl_raw.c` around lines 45
- 48, Before calling palloc to allocate result, check that the computed size
(VARHDRSZ + datalen * 2) does not exceed MaxAllocSize (or otherwise allowable
allocation threshold) and raise a controlled ereport/elog error if it does;
specifically, in the code that computes datalen and assigns result (using
VARHDRSZ, datalen, and palloc), compute the needed_size = VARHDRSZ + datalen *
2, verify needed_size <= MaxAllocSize (or use SizeIsValid/alloc size helper used
in the project), and call ereport(ERROR, ...) with a clear message on overly
large input when the check fails, only then call palloc(needed_size) to assign
result.

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.

1 participant