Path: blob/master/src/java.desktop/macosx/native/libosxapp/JNIUtilities.m
41152 views
/*1* Copyright (c) 2021, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation. Oracle designates this7* particular file as subject to the "Classpath" exception as provided8* by Oracle in the LICENSE file that accompanied this code.9*10* This code is distributed in the hope that it will be useful, but WITHOUT11* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or12* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License13* version 2 for more details (a copy is included in the LICENSE file that14* accompanied this code).15*16* You should have received a copy of the GNU General Public License version17* 2 along with this work; if not, write to the Free Software Foundation,18* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.19*20* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA21* or visit www.oracle.com if you need additional information or have any22* questions.23*/2425#include "JNIUtilities.h"2627NSString* JavaStringToNSString(JNIEnv *env, jstring jstr) {28if (jstr == NULL) {29return NULL;30}31jsize len = (*env)->GetStringLength(env, jstr);32const jchar *chars = (*env)->GetStringChars(env, jstr, NULL);33if (chars == NULL) {34return NULL;35}36NSString *result = [NSString stringWithCharacters:(UniChar *)chars length:len];37(*env)->ReleaseStringChars(env, jstr, chars);38return result;39}4041jstring NSStringToJavaString(JNIEnv* env, NSString *str) {4243if (str == NULL) {44return NULL;45}46jstring jStr = (*env)->NewStringUTF(env, [str UTF8String]);47CHECK_EXCEPTION();48return jStr;49}5051/*52* These next conversion functions are for file system paths.53* The NSString needs to be in de-composed UTF-16 format for the Apple file system54* The Java String needs to be in pre-composed UTF-16 format for display by Java.55* https://developer.apple.com/library/archive/qa/qa1235/_index.html56* has some information on this.57*/5859/*60* Returns an NSString in decomposed UTF16 format that is compatible with HFS's61* expectation of the UTF16 format for file system paths.62*63* Example string: "/Users/Amélie/"64*65* Java's UTF16 string is "/ U s e r s / A m \351 l i e /"66* macOS UTF16 string suitable for HFS is "/ U s e r s / A m e \314 \201 l i e /"67*68* There is no direct API that takes in NSString UTF16 encoded by Java69* and produces NSString UTF16 for HFS, so we first need to decompose it70* into chars (suitable for low level C file APIs), and only then71* create NSString representation of this decomposition back into UTF16 string.72*73* https://developer.apple.com/documentation/foundation/nsstring/1414559-filesystemrepresentation?language=objc74* describes how to get a file system representation as a char* from an NSString75* and then using FileManager (!) convert it to an NSString.76* But we want an NSString.77* So the steps are78* 1) Convert to NSString79* 2) call [NSString fileSystemRepresentation] which gives us a char*80* 3) Convert the returned char* to an NSString using FileManager (is there a better way?)81*/82NSString* NormalizedPathNSStringFromJavaString(JNIEnv *env, jstring pathStr) {83if (pathStr == NULL) {84return nil;85}86NSString *nsStr = JavaStringToNSString(env, pathStr);87if (nsStr == NULL) {88return nil;89}90const char* chs = [nsStr fileSystemRepresentation];91int len = strlen(chs);92NSString* result = [[NSFileManager defaultManager]93stringWithFileSystemRepresentation:chs length:len];94return result;95}9697/*98* Given what is (potentially) a de-composed NSString, convert it to pre-composed99* Then convert it into a Java String.100*/101jstring NormalizedPathJavaStringFromNSString(JNIEnv* env, NSString *str) {102if (str == nil) {103return NULL;104}105NSString *normStr = [str precomposedStringWithCanonicalMapping];106return NSStringToJavaString(env, normStr);107}108109110