Foreign.C.String
Foreign.C.String
C 문자열의 원시 마샬링(primitive marshalling)을 위한 유틸리티 모듈이에요.
본문
module Foreign.C.String (
CString, CStringLen, peekCString, peekCStringLen, newCString,
newCStringLen, withCString, withCStringLen, charIsRepresentable,
castCharToCChar, castCCharToChar, castCharToCUChar, castCUCharToChar,
castCharToCSChar, castCSCharToChar, peekCAString, peekCAStringLen,
newCAString, newCAStringLen, withCAString, withCAStringLen, CWString,
CWStringLen, peekCWString, peekCWStringLen, newCWString,
newCWStringLen, withCWString, withCWStringLen
) where
C 문자열의 원시 마샬링을 위한 유틸리티예요.
마샬링은 유니코드 코드 포인트를 나타내는 각 Haskell 문자를, 기본적으로 현재 로케일(locale)에 의해 결정되는 방식으로 하나 이상의 바이트로 변환해요. 그 결과, Haskell 문자열과 그에 대응하는 C 문자열의 상대적 길이에 대해서는 어떤 보장도 할 수 없기 때문에 모든 마샬링 루틴에는 메모리 할당이 포함돼요. 유니코드와 현재 로케일의 인코딩 사이의 변환은 정보 손실(lossy)이 있을 수 있어요.
27.1 C 문자열 (C strings)
type CString = Ptr CChar
C 문자열은 NUL로 종결되는 C 문자 배열에 대한 참조예요.
type CStringLen = (Ptr CChar, Int)
종결 NUL 대신 명시적인 길이 정보(바이트 단위)를 갖는 문자열이에요(따라서 문자열 중간에 NUL 문자가 있어도 됨).
27.1.1 로케일 의존적 인코딩 사용하기 (Using a locale-dependent encoding)
현재는 이 함수들이 자신의 CAString 대응 함수들과 동일해요. 결국엔 현재 로케일에 의해 결정되는 인코딩을 사용하게 될 거예요.
peekCString :: CString -> IO String
NUL 종결 C 문자열을 Haskell 문자열로 마샬링해요.
peekCStringLen :: CStringLen -> IO String
명시적 길이를 가진 C 문자열을 Haskell 문자열로 마샬링해요.
newCString :: String -> IO CString
Haskell 문자열을 NUL 종결 C 문자열로 마샬링해요.
- Haskell 문자열은 NUL 문자를 포함할 수 없어요.
- C 문자열을 위해 새 저장 공간이 할당되며,
Foreign.Marshal.Alloc.free또는Foreign.Marshal.Alloc.finalizerFree를 사용해 명시적으로 해제해야 해요.
newCStringLen :: String -> IO CStringLen
Haskell 문자열을 명시적 길이 정보를 가진 C 문자열(즉, 문자 배열)로 마샬링해요.
- C 문자열을 위해 새 저장 공간이 할당되며,
Foreign.Marshal.Alloc.free또는Foreign.Marshal.Alloc.finalizerFree를 사용해 명시적으로 해제해야 해요.
withCString :: String -> (CString -> IO a) -> IO a
임시 저장 공간(temporary storage)을 사용해 Haskell 문자열을 NUL 종결 C 문자열로 마샬링해요.
- Haskell 문자열은 NUL 문자를 포함할 수 없어요.
- 하위 계산(subcomputation)이 끝나면(정상 종료든 예외든) 메모리가 해제되므로, 그 이후에는 임시 저장 공간에 대한 포인터를 사용하면 안 돼요.
withCStringLen :: String -> (CStringLen -> IO a) -> IO a
임시 저장 공간에 명시적 길이 정보와 함께 Haskell 문자열을 C 문자열(즉, 문자 배열)로 마샬링해요.
- 하위 계산이 끝나면(정상 종료든 예외든) 메모리가 해제되므로, 그 이후에는 임시 저장 공간에 대한 포인터를 사용하면 안 돼요.
charIsRepresentable :: Char -> IO Bool
문자가 CString에 정확하게 인코딩될 수 있는지 판단해요. 표현할 수 없는 문자는 '?'로 변환돼요.
- 현재는 Latin-1 문자만 표현 가능해요.
27.1.2 8비트 문자 사용하기 (Using 8-bit characters)
위 함수들의 이 변형들은 유니코드를 모르는(ignorant of Unicode) C 라이브러리에서 사용할 수 있어요. 이 함수들은 정보 손실이 발생할 수 있으므로 주의해서 사용해야 해요.
castCharToCChar :: Char -> CChar
Haskell 문자를 C 문자로 변환해요. 이 함수는 처음 256개 문자에 대해서만 안전해요.
castCCharToChar :: CChar -> Char
Latin-1 문자를 나타내는 C 바이트를 대응하는 Haskell 문자로 변환해요.
castCharToCUChar :: Char -> CUChar
Haskell 문자를 C의 unsigned char로 변환해요. 이 함수는 처음 256개 문자에 대해서만 안전해요.
castCUCharToChar :: CUChar -> Char
Latin-1 문자를 나타내는 C의 unsigned char를 대응하는 Haskell 문자로 변환해요.
castCharToCSChar :: Char -> CSChar
Haskell 문자를 C의 signed char로 변환해요. 이 함수는 처음 256개 문자에 대해서만 안전해요.
castCSCharToChar :: CSChar -> Char
Latin-1 문자를 나타내는 C의 signed char를 대응하는 Haskell 문자로 변환해요.
peekCAString :: CString -> IO String
NUL 종결 C 문자열을 Haskell 문자열로 마샬링해요.
peekCAStringLen :: CStringLen -> IO String
명시적 길이를 가진 C 문자열을 Haskell 문자열로 마샬링해요.
newCAString :: String -> IO CString
Haskell 문자열을 NUL 종결 C 문자열로 마샬링해요.
- Haskell 문자열은 NUL 문자를 포함할 수 없어요.
- C 문자열을 위해 새 저장 공간이 할당되며,
Foreign.Marshal.Alloc.free또는Foreign.Marshal.Alloc.finalizerFree를 사용해 명시적으로 해제해야 해요.
newCAStringLen :: String -> IO CStringLen
Haskell 문자열을 명시적 길이 정보를 가진 C 문자열(즉, 문자 배열)로 마샬링해요.
- C 문자열을 위해 새 저장 공간이 할당되며,
Foreign.Marshal.Alloc.free또는Foreign.Marshal.Alloc.finalizerFree를 사용해 명시적으로 해제해야 해요.
withCAString :: String -> (CString -> IO a) -> IO a
임시 저장 공간을 사용해 Haskell 문자열을 NUL 종결 C 문자열로 마샬링해요.
- Haskell 문자열은 NUL 문자를 포함할 수 없어요.
- 하위 계산이 끝나면(정상 종료든 예외든) 메모리가 해제되므로, 그 이후에는 임시 저장 공간에 대한 포인터를 사용하면 안 돼요.
withCAStringLen :: String -> (CStringLen -> IO a) -> IO a
임시 저장 공간에 명시적 길이 정보와 함께 Haskell 문자열을 C 문자열(즉, 문자 배열)로 마샬링해요.
- 하위 계산이 끝나면(정상 종료든 예외든) 메모리가 해제되므로, 그 이후에는 임시 저장 공간에 대한 포인터를 사용하면 안 돼요.
27.2 C 와이드 문자열 (C wide strings)
위 함수들의 이 변형들은 C의 wchar_t 타입을 사용해 시스템 의존적인 방식으로 유니코드를 인코딩하는 C 라이브러리에서 사용할 수 있어요. 지원되는 인코딩은 다음뿐이에요.
- UTF-32 (C 컴파일러가
__STDC_ISO_10646__를 정의하는 경우), 또는 - UTF-16 (Windows 시스템에서 사용되는 방식)
type CWString = Ptr CWchar
C 와이드 문자열은 NUL로 종결되는 C 와이드 문자 배열에 대한 참조예요.
type CWStringLen = (Ptr CWchar, Int)
종결 NUL 대신 CWchar들의 명시적 길이 정보를 갖는 와이드 문자열이에요(따라서 문자열 중간에 NUL 문자가 있어도 됨).
peekCWString :: CWString -> IO String
NUL 종결 C 와이드 문자열을 Haskell 문자열로 마샬링해요.
peekCWStringLen :: CWStringLen -> IO String
명시적 길이를 가진 C 와이드 문자열을 Haskell 문자열로 마샬링해요.
newCWString :: String -> IO CWString
Haskell 문자열을 NUL 종결 C 와이드 문자열로 마샬링해요.
- Haskell 문자열은 NUL 문자를 포함할 수 없어요.
- C 와이드 문자열을 위해 새 저장 공간이 할당되며,
Foreign.Marshal.Alloc.free또는Foreign.Marshal.Alloc.finalizerFree를 사용해 명시적으로 해제해야 해요.
newCWStringLen :: String -> IO CWStringLen
Haskell 문자열을 명시적 길이 정보를 가진 C 와이드 문자열(즉, 와이드 문자 배열)로 마샬링해요.
- C 와이드 문자열을 위해 새 저장 공간이 할당되며,
Foreign.Marshal.Alloc.free또는Foreign.Marshal.Alloc.finalizerFree를 사용해 명시적으로 해제해야 해요.
withCWString :: String -> (CWString -> IO a) -> IO a
임시 저장 공간을 사용해 Haskell 문자열을 NUL 종결 C 와이드 문자열로 마샬링해요.
- Haskell 문자열은 NUL 문자를 포함할 수 없어요.
- 하위 계산이 끝나면(정상 종료든 예외든) 메모리가 해제되므로, 그 이후에는 임시 저장 공간에 대한 포인터를 사용하면 안 돼요.
withCWStringLen :: String -> (CWStringLen -> IO a) -> IO a
임시 저장 공간을 사용해 Haskell 문자열을 NUL 종결 C 와이드 문자열로 마샬링해요.
- Haskell 문자열은 NUL 문자를 포함할 수 없어요.
- 하위 계산이 끝나면(정상 종료든 예외든) 메모리가 해제되므로, 그 이후에는 임시 저장 공간에 대한 포인터를 사용하면 안 돼요.
더 알아보기 (Learn more)
- 문자열 마샬링에 쓰이는 메모리 해제 함수는 31장 Foreign.Marshal.Alloc에서 다뤄요.
- C에서 쓰이는 기본 타입(
CChar,CUChar,CSChar,CWchar등)은 28장 Foreign.C.Types에서 다뤄요.