Fail fast extensions#20605
Conversation
…AsDuckDBExtension
… or moved in default situations For creations, opening a file for writing is forbidden if the relevant flag is missing For moveing A into B, either B is NOT an extension, or both A AND B are extensions Note that this means temporary files are also named ending in '.duckdb_extension'
… extensions are enabled) This enforces that extensions are only loaded if ending in '.duckdb_extension' For development reasons, LOAD <path> is still possible when extension signature checks are disabled
b8eb198 to
03ae81a
Compare
samansmink
left a comment
There was a problem hiding this comment.
Looks great! left a few comments
Mytherin
left a comment
There was a problem hiding this comment.
Looks good - some comments from my side
| target_file->Close(); | ||
| target_file.reset(); | ||
| fs.TryRemoveFile(path); | ||
| throw IOException("Attempting to install an extension file that hasn't a valid signature, see " |
There was a problem hiding this comment.
Maybe use the error manager here similar to what we do for ErrorType::UNSIGNED_EXTENSION so we can override suggestions for it
There was a problem hiding this comment.
Yes, that would be cleaner, but I opted NOT to add them, given this will require changes client side for a patch release.
This can be considered for v1.5.0.
| VerifyCanAccessFile(source); | ||
| VerifyCanAccessFile(target); | ||
| if (StringUtil::EndsWith(target, "duckdb_extension") && !StringUtil::EndsWith(source, "duckdb_extension")) { | ||
| throw PermissionException("File '%s' cannot be moved to '%s' due to the suffix 'duckdb_extension'", source, |
There was a problem hiding this comment.
On that note - we should only check this if allow_unsigned_extensions is enabled.
There was a problem hiding this comment.
It would also be nicer if this was pushed into VerifyCanAccessFile somehow - e.g. by pushing in the action:
VerifyCanAccessFile(source, FileOperationType::MOVE_FILE)There was a problem hiding this comment.
On that note - we should only check this if allow_unsigned_extensions is enabled.
I opted here to implement this independently from allow_unsigned_extensions flag, basically duckdb will never write to files ending in allow_unsigned_extensions, and never move them (but if both are extensions), and signature checks are independent and performed on LOAD or now INSTALL (and those will have the check on allow_unsigned_extensions or whether community extensions are enabled or not.
5586e21 to
e30ba53
Compare
e30ba53 to
3791a27
Compare
|
There are still two comments not properly handled. |
b826c86 to
3abba50
Compare
3abba50 to
9ab4b88
Compare
1347c9d to
d5dcf30
Compare
d5dcf30 to
c195649
Compare
…uffer (already in memory) Use those to check for signature validity BEFORE writing temporary extension file to disk
837b514 to
f0b38e6
Compare
55eaf54 to
1668d9a
Compare
1668d9a to
79b498b
Compare
Fail fast extensions (duckdb/duckdb#20605)
Fail fast extensions (duckdb/duckdb#20605) Co-authored-by: krlmlr <krlmlr@users.noreply.github.com>
Tested on fork's CI to be working, according to changes that landed in #20605. Should make so nightly CI for `v1.4-varieagata` (and later other brances as well) should pass for "Extension updating test".
Changes so that INSTALL also performs signature checks (according to database configuration).
This is somewhat redundant, BUT avoids cases where one might successful install an extension that can't be then loaded.
Logic is as follows:
Basically there are 3 families of files:
B can be created and moved into freely
A can only be created during install path (since it's the only place where we pass the flag, and we will only create B)
A can only be moved into from other A files, while A can be moved to a B
A is the only type of file we would load from