X86 Open로그인

추천하기 twitter 로그인 facebook 로그인 google 로그인 카카오 로그인 네이버 로그인
8

요즘 한창 잠수를 타며 꼬르륵 상태에 있는 KsJ라고합니다..!

정말 오랜만에 다시 키보드를 붙잡고 타이핑을 하려합니다.

 

저번 시리즈는 CPU에 대한 내용으로 이야기를 했었는데, 오늘은? DSDT를 파헤쳐보려합니다.

아마 긴 글이 될 것이라 생각합니다만 최대한 가볍게 풀어보도록 하겠습니다.

 

1. DSDT란?

DSDT는 여러분의 시스템 정보를 총 집약해둔 하나의 정보집합체라고 보시면 되겠습니다.

하여, 이 정보를 가지고 여러가지 장난을 칠 수 있는데- 가령 없는 하드웨어를 있는 것 처럼 속일 수 있는 것을 예로 들 수 있겠습니다.

 

이러한 이유가 가능한 것은, 컴퓨터의 구조상 OS가 부팅순서에 따라 DSDT의 정보를 어느정도 의존하여 동작하기 때문입니다.

그래서 맥 OS를 커스텀하기 위하여 제작된 다양한 부트로더들이 해당 DSDT기능을 지원하는 가장 큰 이유이기도 하며, 실로 어지간한 선에서는

DSDT 만으로 해결이 가능한 경우가 대부분일 정도로 가히 만능이라고 할 수 있겠습니다.

 

하지만 해당 테이블은 ACPI규약에 따라 특수한 언어로 작성되어있어, 가공 및 수정이 별로 용이하지 못하다는 점이며

이를 보안하기 위하여 부트로더들이 자신들만의 특별한 기능이나 옵션을 부가적으로 제공하여 해결을 보려는 것입니다.

 

특히 클로버는 DSDT없는 커스텀맥을 위할 정도로 DSDT와 관련한 대부분의 내용을 클로버 컨피규레이터나 config파일의 수정으로 대신할 수 있을 정도입니다.

하지만, 그 외인 카멜레온이나 Ozmosis의 경우는 별로 그러하지 못하다는 점에 있어- 그리고 클로버도 경우에 따라서는 DSDT에 대한 직접적 수정이 필요하게 되는 때가 존재한다는 점에서 한 번 쯤은 누구나 겪어가게 되는 난감한 부분이라 할 수 있겠습니다.

 

2. DSDT의 구조?

DSDT는 다른 언어와는 조금 다르게, 특수한 트리구조를 가지고 있는 형태로 작성됩니다.

또한 모든 값을 어디서든 요청하여 직접 불러올 수 있다는 점에서 타 언어와는 다른 변수라는 개념이 딱히 없는 형태의 언어라는 것이지요.

 

스크린샷 2016-05-09 오전 11.22.05.png

 

이런식으로 여러가지 폴더가 있는 형태로 만들어져 있다는 것을 보실 수 있습니다.

이러한 부분들은 구조를 잘 파악하여 정리해줄 수 있는 부분들에 속합니다만, 때로 약간의 수정만으로도 파일이 망가지는 구조적 결함이 생기어커널 패닉을 유발하는 원인이 되기도 하기에 수정에는 항상 각별한 주의가 필요합니다.

 

3. DSDT를 수정하기 위한 준비?

DSDT는 여러가지 툴이 있습니다만, 저는 MaciASL을 추천하는 편입니다.

MaciASL은 수정 및 편집이 가장 용이하면서도, ACPI의 버전을 직접적으로 수정하여 적용 버전을 달리 할 수 있기 때문입니다.

 

첨부파일의 MaciASL은 5.1버전까지 지원하는 프로그램입니다.

다운을 받아주신 후에, 아래 설정을 꼭 해주시기 바랍니다.

 

MaciASL을 실행시킨후 Command + , 를 눌러서 환경설정을 열어줍니다.

스크린샷 2016-05-09 오전 11.26.22.png

 

그리고 iASL에서 ACPI를 5.1로 설정해준 후 MaciASL을 재실행해주면 되겠습니다.

 

외로, MaciASL 뿐만 아니라 추가적으로 필요한 정보를 구해야 할 때가 간혹 존재합니다.

이 DSDT가 정말 제대로 적용이 된 것인지 확인하기 위한 것인데, 여러가지 툴 중에서 직접적 수정을 위한 좋은 툴을 첨부합니다.

 

IORegistryExplorer라는 프로그램입니다.

이 프로그램은 여러분의 컴퓨터에 대한 DSDT 정보와 연루된 모든 ACPI테이블을 보기좋게 보여주는 프로그램입니다.

해당 프로그램을 사용하여 정보를 확인하는 방법이 가장 보편적이지만,

 

때로는 터미널에서 ioreg | grep text 를 사용하여 자신이 원하는 정보를 찾아내는 방식을 사용하기도 합니다.

 

4. DSDT의 언어를 알아보자!

DSDT의 첫 블록은 대게 

 

DefinitionBlock ("iASL09MazA.aml", "DSDT", 2, "Apple ", "A M I", 0x00000088)
{

 

}

 

이런식으로 구성됩니다만, 중요한 것은 { }이 되겠습니다.

모든 블록은 () 와 {}의 한 쌍으로만 구성되며 이들 중 하나라도 없는 경우에는 오류가 생깁니다.

 

또한 , (쉼표)도 중요한데이 쉼표는 무엇인가를 여러개 나열할 때 사용되어지는 지표의 역할을 해줍니다.

예컨데 A, B, C, D 라는 것을 구분할때 ,를 사용하여 구분하지만 A, B, C, 는 컴마 뒤에 아무것도 없기에 오류를 뿜습니다.

 

반드시 , 뒤에는 무엇인가 내용이 있어야 한다는 것이지요.

 

외로는 메소드라고 불뤼는 특수한 실행구분이 존재하는데,

메소드 외로 실행구문 및 외부 참조구문, 디바이스 정의구문 등 다양한 구문이 존재합니다.

 

4-1. External

External 의 경우는 외부로부터 무엇인가를 불러와 참조한다는 것을 뜻합니다.

주로 원형은 External (Device or Method or Obj, Type) 형식으로 작성됩니다.

 

예를 들면 External (_SB_.PCI0.PEG0, UnknownObj)를 들 수 있겠는데,

해당 정보는 외부 참조가 _SB_.PCI0.PEG0가 되는 것이고 가져오는 타입은 알려지지 않은 Obj 형식이 되는 것입니다.

 

4-2. Name

Name은 정의구문과 흡사합니다. 일명 Variable (변수)와 같은 존재이며,

해당 구문은 미리 정의되어야하는 값이 있을 때 사용되는 구문입니다.

Name (상수 이름, 값[16진수]) 형태로 작성됩니다.

 

C언어 기준 int K = 0x10 와 흡사합니다.

 

4-3. OperationRegion Field

OperationRegion은 대규모 영역을 지정할 때 사용되는 문구이며 작성은 Field에 작성됩니다.

일명 Struct로 불뤼는 구조체와 같은 역할을 담당합니다.

 

4-4. Scope

Scope는 폴더를 만들 때 사용되는 문구입니다.

해당 폴더는 대게 _SB, _PR이나 여러가지 이름으로 작성되지만, 건드릴 일이 거의 없습니다.

 

4-5. Package

Package는 하나의 묶음단위로써 Array인 배열과 흡사한 존재입니다.

대신 하나의 값만 저장이 가능하지 아니하고, 다양한 값이 저장이 가능한 탓에 AnyObject Array이기도 합니다.

 

대게 작성 형태는 아래를 따릅니다

 

Package (항목 갯수[16진수])

{

    1번째 항목,

    2번째 항목,

    3번째 항목,

    .

    .

    .

    n번째 항목

}

 

4-6. Method

Method는 일종의 실행구문으로써 함수와 비슷한 기능을 수행하는 문구입니다.

대게 작성은 아래와 같이 작성됩니다.

 

Method (함수명, 사용되는 인수 값의 갯수, NotSerialized or Serialized)

{

    내용

    Return (Zero or Other Value)

}

 

함수인 만큼 반환값이 따로 존재하여, 값이 반환되지 않는 경우에는

Not all control paths return a value 와 같은 경고문구가 나타나게됩니다.

 

4-7. If

조건문으로써 Else와 같이 사용되는 문구입니다. 유감스럽게도 Else If 구문은 존재하지 않습니다.

대게 If문은 비교대상 1, 비교연산자, 비교대상 2 순으로 작성되는 것이 관례이지만 유닉스 혹은 리눅스 계열이나 시스템 계열에서는 이 형식이 조금 다르게 작성되는 것이 관례입니다.

 

아래를 예로 들 수 있겠습니다.

If (LEqual (비교대상 1, 비교대상 2))

{

   수행 구문

}

 

이 경우 LEqual은 왼쪽이 우측과 같으면이라는 의미를 지닙니다.

이런 식으로 비교 연산자 대신, 비교해주는 작은 함수를 호출하여 기능을 수행합니다.

여기에 사용되는 다른 연산자로 Or과 And도 존재하며 다른 언어와 마찬가지로 중복 사용이 가능합니다.

 

4-8. While

While구문은 특정 조건을 충족하는 동안에 계속 반복 실행하는 구문입니다.

주로 For문이 많이 사용되는것에 비하여 DSDT에서는 유일하게 While구문만이 사용됩니다.

 

아래는 기본적인 사용 예제입니다.

While (LGreater (비교대상 1, 비교대상 2))

{

   반복 수행할 내용

}

 

이 경우 LGreater는 비교대상 1보다 비교대상 2가 큰 경우, 혹은 그 역인 경우가 참일 동안에 반복되는 것을 뜻합니다.

외로는 LAnd, LOr, LLess등이 사용됩니다.

 

4-9. Store

값의 저장을 말해주는 Store입니다. 대게 변수에 값을 대입하는 것과 비슷한 역할이라 보시면 되겠습니다.

 

사용예제는 아래와 같습니다

Store (값, 변수)

 

4-10. Return

값의 반환을 담당합니다. 다른 언어와는 달리 반환 값은 함수가 될 수도 있습니다.

 

사용예제는 아래와 같습니다

Return (값 or 변수 or 메소드)

 

주로 DSDT에서는 아래와 같이 사용됩니다.

Method (_PRW, 0, NotSerialized)

{

    Return (GPRW (0x09, 0x04))

}

 

이 경우 GPRW라는 메소드에 0x09, 0x04라는 인자값이 사용되어 함수가 반환되는 것을 볼 수 있습니다.

 

4-11. Device

단순히 기기를 하나 만들어주는 특수 메소드입니다.

 

Device (기기 이름)

{

  기기 정보

}

 

위와같은 형식으로 사용됩니다.

 

4-12. Processor

Processor는 유일하게 CPU관련 구문에 관하여서만 사용되는 구문입니다.

프로세서 또한 일종의 메소드이므로 작성은 아래와 같이 작성됩니다.

 

Processor (CPUX, 0x0X, 0x0000XXXX, 0x0X)

{

    프로세서 정의구문

}

 

5. DSDT를 건드려보기!

1. 기본적 수정

DSDT에 대한 언어를 살펴본 이유는 다음과 같습니다.

적어도 어떻게 수정해야하는지와 기본적 공자가 어떻게 되어있는지를 미리 살펴봄으로써, 실질적으로 수정을 해야할 때

잘못된 수정으로 인하여 생기는 오류를 미연에 방지할 수 있기 때문입니다.

 

우선, DSDT는 AML이라는 파일로 저장되는데 이 파일은 Encryption형식의 파일입니다. 한마디로 컴파일된 파일 형식이라는 것이지요.

그로 인하여 파일용량이 대게 40KB~60KB로 작성되는 것이 특징입니다.

 

하지만 이 형식으로 저장하기 위해서는 컴파일이 되어야하는데, MaciASL의 컴파일을 누르면 빨간 Error메시지가 나오면서

저장이 되지 않는 것 때문에 너무나도 골치를 썩는다는 것이 문제입니다.

 

여러분은? 이제 영어랑 친해지셔야합니다. 

영어라 덜컥 겁먹으실 필요는 없다는 것이죠, 컴파일러는 친절하게 뭐가 문제인지 여러분에게 말해주고 있을 뿐이랍니다.

[그게 영어라는게 문제긴 합니다 -_-..]

 

또한 Warning이나 Remarks는 별로 신경쓸 필요가 없습니다.

순수하게 컴파일되어 저장하는 것은 ERROR만 해결해주면 되기 때문입니다.

 

DSDT 건드리기는 특별한 내용이 없다는 것이 함정입니다 :)

왜냐하면 오류가 너무나도 다양하여 패치방법을 구글링하여 찾아 해결하셔야 하는데,

대부분 못하겠어요!의 주 원인이 어디다 넣어야 할지를 모르겠어서 혹은 넣기는 넣었는데 오류가 나서 라는 것입니다.

 

우선적으로, 여러분은 여러분의 DSDT를 패치해주기 이전에

기본적으로 생겨난 ERROR메시지를 없애는 데에 심혈을 기울이셔야합니다.

 

그런 후에 ERROR가 사라지면, 그 때 패치해주고 싶은 내용을 패치해주는 것입니다.

그냥 MaciASL을 열고 패치해주고 저장하면 되는.. 그런류가 아니라는 것이지요.

 

이제부터는 실제 문구를 가지고 블럭의 개념을 잡아볼 것입니다.

이 블럭의 개념은 대단히 중요합니다.

 

항상 {와 }는 한 쌍이 셋트이고, (와 )도 한 쌍이 셋트임을 명심하여 작업해야 하기 때문입니다.

 

아래는 실제 제 DSDT에 들어간 구문입니다.

Scope (_PR)
    {
        Processor (CPU0, 0x01, 0x00001810, 0x06)
        {
            Method (_DSM, 4, NotSerialized)  // _DSM: Device-Specific Method
            {
                Store ("Method _PR.CPU0._DSM Called", Debug)
                If (LEqual (Arg2, Zero))
                {
                    Return (Buffer (One)
                    {
                         0x03                                             /* . */
                    })
                }

                Return (Package (0x02)
                {
                    "plugin-type", 
                    One
                })
            }
        }

        Processor (CPU1, 0x02, 0x00001810, 0x06) {}
        Processor (CPU2, 0x03, 0x00001810, 0x06) {}
        Processor (CPU3, 0x04, 0x00001810, 0x06) {}
        Processor (CPU4, 0x05, 0x00001810, 0x06) {}
        Processor (CPU5, 0x06, 0x00001810, 0x06) {}
        Processor (CPU6, 0x07, 0x00001810, 0x06) {}
        Processor (CPU7, 0x08, 0x00001810, 0x06) {}
    }

 

만약 여기에 여러분이 손을 대야 하신다면, 어떻게 손을 대셔야 할지 막막할 것입니다.

그러나 걱정하지 마세요. {와 }는 하나가 쌍이다! 그리고 (와 )도 한 쌍이다!를 기억하기만 하면 되니까요.

 

잘 보면 

Scope (_PR)
    {

로 {가 1개 시작되었습니다.

그리고 마무리는 }로 되어야겠지요.

 

Scope (_PR)

{

   내용

}

 

이런 식이어야 문제가 없다는 것을 여러분은 아실것입니다.

앞서 살펴보았듯이 Processor는 하나의 메소드로써 {}를 한쌍으로 가진 녀석이라 하였습니다.

그렇다면? 

 

앞서 살펴본 문구에서 Processor (CPU1, 0x02, 0x00001810, 0x06) {}는 하나의 셋트로 온전한 문구이니

이 문구들이 총 8개가 있으므로 _PR의 마지막 }는

 

    Processor (CPU7, 0x08, 0x00001810, 0x06) {}
}

이렇게 CPU7메소드 다음의 }임을 알 수 있는 것입니다.

 

만약 여러분이 CPU7 메소드에 CPU0 메소드의 내용을 넣어주어야 한다면?을 가정해보겠습니다.

우선 CPU0에 들어간 Method를 살펴보니 _DSM메소드라는 것이 보입니다.

 

이 메소드 또한 {}가 하나의 셋트인데 끝나는 지점이 무려 5개나 됨을 알 수 있습니다.

 

Processor (CPU0, 0x01, 0x00001810, 0x06)
        {
            Method (_DSM, 4, NotSerialized)  // _DSM: Device-Specific Method
            {
                Store ("Method _PR.CPU0._DSM Called", Debug)
                If (LEqual (Arg2, Zero))
                {
                    Return (Buffer (One)
                    {
                         0x03                                             /* . */
                    }) << 5번째 지점
                } << 4번째 지점

                Return (Package (0x02)
                {
                    "plugin-type", 
                    One
                }) << 3번째 지점
            } << 2번째 지점
        } <<  1번째 지점

 

천천히 살펴보도록 하겠습니다.

 

1번째 지점은, Processor가 처음으로 {로 열렸으니 }로 닫힐 것이고, 그 안에 무언가가 들어가야 하므로

1번째 지점의 }는 Processor 메소드의 한쌍임을 알 수 있습니다. 따라서 탈락입니다.

 

2번째 지점은 그 다음 쌍인 Method의 것이라는걸 알 수 있습니다!

왜냐하면 메소드는 {}로 한 쌍이어야 하는데 안에 어떤 내용물이 들어가있다고 생각할 때 2번째 }는 메소드의 }말고는 유력한 후보가 없다는 것이지요.

 

그렇다면 3번째인 })는 어떤 것일까요? 바로

 

Return (Package (0x02)
                {
                    "plugin-type", 
                    One
                })

 

이것의 한 쌍이라는 것입니다.

앞서 살펴본 바에 따르면 패키지도 {}로 한 쌍이어야 함을 알 수 있는데,

패키지의 내용을 그대로 따라서 제거해주면 아래와 같이 되기 때문입니다.

 

Return ()

 

그리고 그 위인 4번째 지점의 }는 바로 IF문의 것이라는걸 알 수 있습니다.

IF문도 {}로 한쌍이어야 하기 때문입니다.

 

따라서 

 

Return (Buffer (One)
                    {
                         0x03                                             /* . */
                    })

를 무시하고 If문을 적어준다면?

 

If (LEqual (Arg2, Zero))

{

 

}

 

가 되는 것입니다. 이 조건문 안에 반환 값이 들어가게 되는 것이구요.

따라서 CPU0의 _DSM메소드를 아래처럼 긁을 수 있습니다.

 

Method (_DSM, 4, NotSerialized)  // _DSM: Device-Specific Method
            {
                Store ("Method _PR.CPU0._DSM Called", Debug)
                If (LEqual (Arg2, Zero))
                {
                    Return (Buffer (One)
                    {
                         0x03                                             /* . */
                    })
                }

                Return (Package (0x02)
                {
                    "plugin-type", 
                    One
                })
            }

 

이제 이것을 CPU7에 넣어주면 되는 것이지요.

넣을 때도 {}인 한 쌍 안에다가 넣어주기만 하면 됩니다.

 

{

    내용

}

식으로 말이지요.

 

이렇게 기본적인 원리만 지켜주신다면 특별한 오류 없이도 충분히! 해결하실 수 있을거라 확신합니다.

아무래도 오류를 수정함에 있어 기본적 문법을 간과하게되는 경우가 많다보니, 해결법만 그대로 따라하게더라는 문제가 생기더라구요.

 

2. 경로 추적 및 기기 경로 추가

이제는 경로 추적 및 기기 경로 추가라는 조금 어려운 것을 시도해보려고 합니다.

이것은 실제로 여러분의 디바이스를 인식시켜주기 위하여 Device메소드를 사용하여 DSDT에 기기를 생성시켜주는 작업을 하는 것입니다.

 

우선 첨부파일의 IORegistryExplorer를 다운받아 실행시켜줍니다.

그러면 좌측에 아래와 같은 사진처럼 트리구조가 나오게됩니다.

 

스크린샷 2016-05-09 오후 12.48.35.png

 

이것들을 주르륵 내려주어 PCI0을 찾아줍니다.

스크린샷 2016-05-09 오후 12.49.43.png

 

이렇게 여러가지 트리구조가 보이는데, 너무 복잡하므로 AppleACPIPCI 에 소속된 값들을 정리해주려고 합니다.

바로 아래에 있는 것만 정리하면됩니다.

 

정리는 역삼각형 모양을 누르면 됩니다.

스크린샷 2016-05-09 오후 12.50.47.png

 

짜잔! 보기좋게 정리하면 위의 모습처럼 나오게 됩니다.

이제 이것들을 토대로 간단한 작업을 해보려고 합니다.

 

잘 보시면 EHC2등등 이름 오른쪽에 @~~ 로 되어있는 것이 보이실겁니다.

이것이 바로 기기 경로주소이며, DSDT에 기기를 추가해주거나 인식시켜줄 때 사용되는 중요한 값입니다.

 

DSDT를 열어서 위의 이름들로 검색을 한번 수행해봅니다.

그런데 도저히 Device메소드로는 보이지 않습니다. 어떻게 추가해야할까요?

 

기본 룰은 아래를 따릅니다.

 

위 IOREGISTRY에 따르면, 해당 기기 정보들은 PCI라는 곳에 소속되어있음을 알 수 있습니다.

이렇게 어떤 상위구조에 하위구조가 속해진 경우 대게는 Scope나 Device로 그룹화되어 관리되는 것이 관례입니다.

 

따라서 PCI랑 관련된 폴더나 기기를 찾아봅니다.

스크린샷 2016-05-09 오후 12.54.17.png

 

잘 찾아보니 PCI0기기가 보입니다. _SB폴더 안에 있네요.

그런데 폴더를 잘 보니 _SB.PCI0이라는 폴더가 또 보입니다.

 

이것은 하나의 PCI0 기기에 들어갈 내용이 2개로 분리되어 작성된 것을 의미합니다.

그 아래의 .~이 붙은 것들은 PCI0의 하위에 해당되는 내용이므로 저희가 찾는 것이 아닙니다.

 

스크린샷 2016-05-09 오후 12.55.37.png

 

폴더를 열어보니 위에서 살펴본 기기들이 한 곳에 몰려있는 것을 볼 수 있습니다.

드디어 찾은 것이지요!

 

저희는 pci8086,8c3d@16,3을 DSDT에서 살펴보도록 하겠습니다.

분명 기기는 맞는데 이름이 저렇게 나왔다는 것은 뭔가 있다는 것이겠죠?

 

다른 기기처럼 이름을 만들어주기 위하여

Device (KT)

{

 

}

라는 이름으로 기기를 하나 생성시켜줍니다.

추가하는 위치는 다른 기기들이 있는 곳에 작성해주면 되겠습니다.

 

스크린샷 2016-05-09 오후 12.59.06.png

 

저런 경우에 추가하는 위치는 }와 Device (EHC1)의 사이인

빈줄에 추가하면 되겠습니다.

 

아래처럼 말이지요.

 

Device (MCHC)

{

    내용

}

 

Device (KT)

{

    내용

}

 

Device (ECH1)

...

 

저는 저기 말고 아래처럼 추가해주었습니다.

 

스크린샷 2016-05-09 오후 1.00.20.png

 

 

잘 보시면 KT안에 Name(_ADR, ~~~)라는 값이 들어가있는걸 알 수 있습니다.

이것은 바로 기기 주소값을 지정해주는 문구로써 저희가 IORegi에서 살펴본 값으로 작성됩니다.

 

/** 아래 내용은 HackBook님의 제보로 수정되었습니다 ! [감사합니다 ^^] **/

 

[변경 전]

0x0016 3000이라는 것은

@오른쪽에 16,3을 기준으로 16, 우측은 3000의 1번째인 3이 되는 것을 뜻합니다.

예로 2D,94라는 것이 있다면 경로 주소는 0x002D 9400이 되는 것입니다.

 

[변경 후]

위 사진은 잘못된 부분이에요. 혼란스럽게 해드려서 죄송합니다!

@오른쪽 16,3을 기준으로 16은 0x0016이되고, 3은 맨 끝자리인 0x00000003이 되는것이 맞습니다.

따라서 @16,3은 0x00160003이 되어야합니다.

예시로 든 2D,94는 0x002D0094가 된다고 보시면 되겠습니다. :]

 

----------------------------------------------------------------------------

 

이렇게 기본적인 기기를 추가해줄 수 있고 _DSM메소드를 넣음으로써 특별한 기기 정보를 수정하기도 합니다.

 

Method (_DSM, 4, NotSerialized)  // _DSM: Device-Specific Method
            {
                Store ("Method _SB.PCI0.IGPU Called", Debug)
                If (LEqual (Arg2, Zero))
                {
                    Return (Buffer (One)
                    {
                         0x03                                             /* . */
                    })
                }

                Return (Package (0x02)
                {
                    "AAPL,ig-platform-id", 
                    Buffer (0x04)
                    {
                         0x07, 0x00, 0x26, 0x0D                           /* ..&. */
                    }
                })
            }

 

이런 _DSM메소드는 수정하는 방식이 따로 있는데,

Return (Package (0x02)
                {
                    "AAPL,ig-platform-id", 
                    Buffer (0x04)
                    {
                         0x07, 0x00, 0x26, 0x0D                           /* ..&. */
                    }
                })

 

이 값을 기본적으로 수정하게됩니다.

 

리턴 우측의 Package (0x02)는 하위 요소가 2가지라는 것을 의미합니다.

여기서는 "AAPL,ig-ploatform-id"와 Buffer (0x04) {}가 됩니다.

 

만약 이 두가지 말고 "Name"을 추가하고 싶은 경우라면

버퍼 {} 마지막에 ,로 구분자를 하나 추가해준 후 추가 작성을 하시면 됩니다.

 

Return (Package (0x02)
                {
                    "AAPL,ig-platform-id", 
                    Buffer (0x04)
                    {
                         0x07, 0x00, 0x26, 0x0D                           /* ..&. */
                    }, << 컴마로 구분

                    "Name", 
                    Buffer (0x04)
                    {
                         "Nvidia GTX 950Ti"                           /* ..&. */
                    } << 마지막은 컴마가 없음
                })

 

여기서 오류가 하나 나는데 Return의 패키지 값은 분명 0x02로 2개인데, 저희가 2개를 더 넣음으로써 총 4개가 되어버렸습니다.

따라서  Return (Package (0x02)는 Return (Package (0x04)로 변경되어야합니다.

 

그리고, Name아래의 버퍼값은 4개를 의미하는데, 기입된 글자 수는 17자입니다. (글자 16자에 마지막 문자열 종료가 추가되어 +1이됩니다)

따라서 17을 16진수인 0x11로 변환하여 0x04대신 넣어주어야 합니다.

 

Return (Package (0x04)
                {
                    "AAPL,ig-platform-id", 
                    Buffer (0x04)
                    {
                         0x07, 0x00, 0x26, 0x0D                           /* ..&. */
                    }, << 컴마로 구분

                    "Name", 
                    Buffer (0x11)
                    {
                         "Nvidia GTX 950Ti"                           /* ..&. */
                    } << 마지막은 컴마가 없음
                })

 

위 처럼 최종적으로 수정이 완료되어야 하는 것입니다.

그리고 이 값은 기존 _DSM에 추가 수정되어 아래처럼 만들어지게 됩니다.

 

Method (_DSM, 4, NotSerialized)  // _DSM: Device-Specific Method
            {
                Store ("Method _SB.PCI0.IGPU Called", Debug)
                If (LEqual (Arg2, Zero))
                {
                    Return (Buffer (One)
                    {
                         0x03                                             /* . */
                    })
                }

               

                Return (Package (0x04)
                {
                    "AAPL,ig-platform-id", 
                    Buffer (0x04)
                    {
                         0x07, 0x00, 0x26, 0x0D                           /* ..&. */
                    }, << 컴마로 구분

                    "Name", 
                    Buffer (0x11)
                    {
                         "Nvidia GTX 950Ti"                           /* ..&. */
                    } << 마지막은 컴마가 없음
                })


            }

 

이제 좀 감히 잡히시는지요?

이런 _DSM문구들은 앞서 작성된 Device 안에 들어가게되는 문구들입니다.

 

6. DSDT와 관련된 자료들

글을 마무리하기에 앞서, 제가 기존에 DSDT와 관련하여 작성한 링크들을 추가로 기재해봅니다.

패치방법이 많이 바뀌어 그대로 적용할 수 없는 것들이 많지만 적어도 도움이 되었으면 하는 바람에서 남겨둡니다.

 

DSDT를 수정하는데 있어서 필요한 최소한의 팁 v1.2

[DSDT 정복하기 1강] 더이상 DSDT를 두려워하지 말자!

[DSDT 정복하기 2강] 기본적인 오류 수정하기

[DSDT 정복하기 3강] DSDT의 구조와 다른 테이블을 알아보자 (+ dsdt 정리하기)

[DSDT 정복하기 4강] IORegistryExplorer를 사용하여 켁스트 로드하기

BCM94360CD 를 위한 DSDT 패치.

 

7. 글을 마무리하며

글을 마무리하며,, 몇가지 첨언을 해보려합니다.

커스텀맥 자체가 원래 끈기를 많이 요하는 부류에 속해있습니다만, DSDT도 그러하다고 많이 생각합니다.

빠르게 패치하고 빠르게 적용하고 싶은 바람은 알겠지만, 단순히 오류 수정을 요청하시어 글을 남겨주시는 분들을 보면

때로는 죄송하게도, 별로 패치해주고 싶은 생각이 들지 않는 경우가 많더라는 것이지요. [이러면 안되는데도 말입니다]

 

그리고 가장 난해한 것이 DSDT라는 부분인 것 같습니다. 

이 DSDT에 사용되는 좀 더 구체적인 내용은 ACPI Table과 관련된 메뉴얼을 참고하면 알 수 있는데, 페이지만 500페이지에 육박합니다.

엄청난 페이지이고 모든 내용을 저희가 다 알기엔 무리가 있다는 것이지요.

 

하여, 요번 글은 아주 기본적인 문법과 수정법에 관련해서만 글을 작성하게 되었음을 글을 마치고서야 밝힙니다 ^^*

많이 불친절한 글이기는 합니다만, 이런 글은 많을 수록 좋다는 것이 저의 개인적인 견해인지라...

작성함에 있어 많이 부족함을 느낌에도 불구하고 글을 남깁니다.

 

긴 글 읽어주셔서 감사드리며,

즐거운 커맥라이프 되시길 바라겠습니다.

 

감사합니다 :]

good poor

하이퍼즈몰 Bac soy567 D'Artagnan 일축 HackBook Ativ9Lite xpandi님
8명이 이글을 호평하셨습니다. -1명이 불평하셨습니다.

★ 글쓴이에게 고마우시면 커피한잔 후원(클릭) ★ 추천 정보가 입력되지 않았습니다.
twitter 공유 facebook 공유 googleplus 공유 카카오스토리 공유 네이버라인으로 공유

글쓴이의 서명이 비어 있습니다.

★ 글쓴이에게 고마우시면 커피한잔 후원(클릭) ★ 추천 정보가 입력되지 않았습니다.
  • Profile
    2016/05/09
    0 0
    우와~ 매번 좋은 강의 잘보고있습니다!^^ 덕분에 많은걸 배우게 되네요~ 감사합니다~ㅋ
  • Profile
    2016/05/09
    0 0
    xpandi : 우와~ 매번 좋은 강의 잘보고있습니다!^^ 덕분에 많은... 에 달린 대댓글입니다.
    읽어주심에 감사드립니다, xpandi님!
  • Profile
    2016/05/09
    0 0
    오랜만의 강의 감사합니다~!
    저도 DSDT 수정을 처음엔 의뢰했지만, 그걸 바탕으로 추출부터 차근차근 몇일에 걸쳐해보니 익숙해지더군요, 
    아직도 완벽하진 않지만, 끈기를 가지고 천천히 제대로 짚고 넘어가니 이젠 두렵지 않습니다.!!!

  • Profile
    2016/05/09
    0 0
    Ativ9Lite : 오랜만의 강의 감사합니다~!저도 DSDT 수정을 처음엔 ... 에 달린 대댓글입니다.
    DSDT가.. 건드리는게 어렵다 어렵다라는 말이 많아서 더 어려운걸지도 모르겠단 생각이에요.
    아티브님처럼 꾸준히 빠샤하면 (?) 충분히 건드릴 수 있는 영역이라고 봅니다.

    읽어주셔서 감사드려요!
  • Profile
    2016/05/09
    1 0
    예시로 든 KT 디바이스 어드레스가 이상하군요. @16,3 이라면 0x00160003 이 맞는 것 같은데, 확인 부탁드려요.
    암튼, 추천 꾹!!
  • Profile
    2016/05/09
    0 0
    HackBook : 예시로 든 KT 디바이스 어드레스가 이상하군요. @16,3 ... 에 달린 대댓글입니다.
    엇, 예시를 잘못들어버렸군요!
    빠른 시일 내로 수정하도록 하겠습니다 ;]
    알려주셔서 감사해요 ^^
  • Profile
    2016/05/10
    0 0
    개념이 없었는데 읽으면서 이런거구나 하게 됩니다. 잘읽었습니다. 매번 좋은 글 감사합니다^^
  • Profile
    2016/05/10
    0 0
    일축 : 개념이 없었는데 읽으면서 이런거구나 하게 됩니다. 잘... 에 달린 대댓글입니다.
    이 글이 도움이 되었다니, 감사할 따름입니다.
    읽어주심에 감사드립니다. ^^*
  • Profile
    2016/05/12
    0 0
    좋은 강의 감사합니다.
    시간 될 때 정독해야 겠습니다..^^
  • Profile
    2016/05/19
    0 0
    애플맨 : 좋은 강의 감사합니다.시간 될 때 정독해야 겠습니다..^^ 에 달린 대댓글입니다.
    감사합니다!
  • 2016/05/19
    0 0
    와우 봐도 봐도 어렵네요 ㅜㅜ
    정독 해봐야 겠네요
  • Profile
    2016/05/19
    0 0
    goldbat : 와우 봐도 봐도 어렵네요 ㅜㅜ정독 해봐야 겠네요 에 달린 대댓글입니다.
    내용이 어쩌다보니 너무 길어진거같아요 ;ㅁ;..
    정독 파이팅입니다!! =D
  • Profile
    2016/05/20
    0 0
    역시 어렵 ㅠㅠ
  • Profile
    2016/05/20
    0 0
    SeaSeal : 역시 어렵 ㅠㅠ 에 달린 대댓글입니다.
    포기하지 마시고 천천히 해나가시면.. 될거에요!!
  • Profile
    2016/06/02
    0 0
    존경합니다!!!!!!!!!!
  • Profile
    2016/06/02
    0 0
    soullees : 존경합니다!!!!!!!!!! 에 달린 대댓글입니다.
    헛.. 존경이라뇨, 말씀만으로도 넘 감사드립니다 ㅜㅜ*
  • Profile
    2016/06/13
    0 0
    배워야 할것이 많네요....감사합니다.
  • Profile
    2016/06/13
    0 0
    민엽데디 : 배워야 할것이 많네요....감사합니다. 에 달린 대댓글입니다.
    읽어주심에 감사드립니다!!
  • 2016/07/25
    0 0
    어렵긴한데 정말 좋은 자료네요 정독해야겠어요 해킨은 파면 팔수록 끝이없네요 ㅠㅠ
  • Profile
    2016/07/25
    0 0
    soy567 : 어렵긴한데 정말 좋은 자료네요 정독해야겠어요 해킨은... 에 달린 대댓글입니다.
    그래서 어느정도 선에서 스탑을 외쳐야할지 정해야하는 고스톱과 같다죠 ㅎㅎㅎ
  • Profile
    2016/07/25
    0 0
    KsJ : 그래서 어느정도 선에서 스탑을 외쳐야할지 정해야하는... 에 달린 대댓글입니다.

    4고하려다가 많이들 3점으로 당하죠....

    스톱....

    다시 처음부터...

    그래서

    을지문덕이 우중문에게 보내는 시를 좋아합니다.

    만족함을 알고 물러나라...

  • Profile
    2016/07/25
    0 0
    아이뱅크 : 4고하려다가 많이들 3점으로 당하죠.... 스톱.... ... 에 달린 대댓글입니다.
    갈꺼라면 마지막까지 가줘야하는데, 그렇지 못하달까요..
  • Profile
    2016/07/25
    0 0
    KsJ : 갈꺼라면 마지막까지 가줘야하는데, 그렇지 못하달까요.. 에 달린 대댓글입니다.

    저는 간이 콩알만해서..

    남자라면.....이렇게 호통 못칩니다.

     

  • Profile
    2016/08/06
    0 0

    글잘읽었습니다. 상세한 설명 감사드립니다. 덕분에 개념좀 잡았네요

일반로그인 twitter 로그인 facebook 로그인 google 로그인 카카오 로그인 네이버 로그인
서버에 요청 중입니다. 잠시만 기다려 주십시오...