[Cocoa] Fix deprecated SEL cast in sel_registerName (issue #3186)#3194
Open
HeikoKlare wants to merge 1 commit intoeclipse-platform:masterfrom
Open
Conversation
The Clang compiler (-Wcast-of-sel-type) deprecates any direct cast of the Objective-C SEL type to an arithmetic or pointer type, recommending the use of sel_getName() instead. The warning appeared in os.c: rc = (jlong)sel_registerName(lparg0); // warning: cast of type 'SEL _Nonnull' to 'jlong' is deprecated; // use sel_getName instead [-Wcast-of-sel-type] Rather than routing through sel_getName() (which returns a const char* that would still require an integer cast), the fix applies the same pattern already used for objc_msgSend throughout SWT: the `flags=cast` JNI generator annotation, which casts the entire C function pointer to the desired return type instead of casting the returned value: rc = (jlong)((jlong (*)(const char*))sel_registerName)(lparg0); This avoids any explicit cast of the SEL value itself. The function pointer cast tells the compiler that the function returns jlong directly, bypassing the SEL type in the return position entirely. This is semantically safe on 64-bit platforms where SEL (a pointer) and jlong are both 8 bytes with the same bit representation. The annotation changes in OS.java drive the code generation: - @method flags=cast — use function-pointer-cast call pattern - @param selectorName cast=(const char*) — match the native signature
Contributor
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Issue
Clang emits a
-Wcast-of-sel-typedeprecation warning in the auto-generatedos.cwhensel_registerNamereturns aSELthat is directly cast tojlong:This warning is part of a broader set of deprecation warnings in the macOS/Cocoa native implementation tracked in issue #3186. Eliminating all such warnings is a prerequisite for enabling
-Werrorin the native build.Solution options considered
Several approaches were investigated before arriving at the final solution.
❌ Direct intermediate cast:
(jlong)(uintptr_t)sel_registerName(...)Adding an intermediate
uintptr_tcast does not help — the compiler treats any cast from aSELvalue to any type (integer or pointer) as deprecated:Same result with
void*orconst char*as intermediate types — the-Wcast-of-sel-typewarning fires for any explicit cast from aSELvalue regardless of the target type.❌ Using
sel_getName:(jlong)(uintptr_t)sel_getName(sel_registerName(...))The compiler's suggestion — routing through
sel_getName(SEL) → const char*— eliminates the deprecated cast. This was implemented viaflags=no_geninOS.javaand a hand-written function body inos_custom.c. It works correctly, but has two drawbacks: it calls an extra runtime function and moves the implementation out of the auto-generatedos.cintoos_custom.c, which is harder to maintain.Note: the build in the aarch64 fragment folder regenerates
os.cfromOS.javaannotations on each run, so any annotation-based approach must work with the compiled JNI generator in the Maven toolchain — not just the source.✅ Function-pointer cast:
((jlong (*)(const char*))sel_registerName)(lparg0)The fix applies the same pattern SWT already uses for all
objc_msgSendvariants. Instead of casting the value returned bysel_registerName, the function pointer itself is cast to declare a different return type:The compiler sees no cast of a
SELvalue at all — the function is declared (via its retyped pointer) as returningjlongdirectly. This is semantically safe on all 64-bit Apple platforms whereSEL(an 8-byte opaque pointer) andjlongshare the same size and representation.This approach is driven entirely by two JNI generator annotations in
OS.java, keeping the implementation inside the auto-generatedos.c:flags=cast— instructs the generator to emit a function-pointer cast rather than a direct callcast=(const char*)— matches the native C parameter typeconst char*in the cast signatureChanges
OS.java: adds@method flags=castand@param selectorName cast=(const char*)annotations tosel_registerNameos.c: updated generated function body (reflects what the generator produces from the new annotations)Test plan
binaries/org.eclipse.swt.cocoa.macosx.aarch64fragment usingmvn clean process-resources -Dnative=cocoa.macosx.aarch64— confirms the-Wcast-of-sel-typewarning is goneos.c:1102:CFURLCreateFromFSRef— deprecated macOS 10.9os.c:1920:GetCurrentProcess— deprecated macOS 10.9os.c:2119:LSGetApplicationForInfo— deprecated macOS 10.10os.c:4040:NSPrintSavePath— deprecated macOS 10.6os.c:4678:SecPolicySearchCopyNext— deprecated macOS 10.7os.c:4694:SecPolicySearchCreate— deprecated macOS 10.7os.c:4883: passing arguments to a function without a prototype[-Wdeprecated-non-prototype]Notes
This change was developed with the assistance of Claude Code (claude-sonnet-4-6). Multiple solution approaches were explored interactively, including direct casts,
sel_getNamerouting,no_gen+os_custom.c, and the final function-pointer cast pattern.Contributes to #3186.