小黑T410完美DSDT的研讨,不再为睡眠唤醒死机而发愁!(放出完美DSDT,也可支持CLOVER)
本帖最后由 gcafrk 于 2013-1-25 11:34 编辑首先,感谢x5115x提供了一个相对比较完整的THINKPAD T410在MAC下的DSDT修改的详细教程!使得很多略有程序代码经验的T410使用者能够自己动手修改DSDT。
在x5115x的帖子中,提到了以下几个修改:
1)添加DGTP;
2)修改LPC,支持原生电源管理;
3)修改RTC,防止CMOS重置;
4)添加显卡代码(我用了少量的代码+变色龙自动侦测,使得机器可以支持VGA的镜像输出);
5)添加关机断电代码;
6)添加声卡代码;
这些修改对于T410能跑MAC是非常重要和必须的。
经过长达一年多的使用实践,很多朋友都发现目前T410的DSDT虽然可以让机器比较正常地跑,但是确实还有不少毛病(感觉不够完美)。比如:
1)连续多次的睡眠唤醒后,偶尔死机。
2)睡眠唤醒之后,插入U盘死机。
虽然我们可以设置不让机器睡眠,从而避免死机的问题出现。但是,从完美角度来说,毕竟这是一块心病!
从DSDT修改的角度,一方面是尽量向MAC的DSDT靠近。但是从另一方面来说,也得充分考虑到硬件自身的一些特性参数。因此,生搬硬套DSDT的修改代码,的确会造成系统在使用中偶尔出现(甚至频繁出现)的毛病。
MAC OSX系统会在读取DSDT.AML文件之后,加载其中与硬件对应的“设备”。因此,我们可以通过IORegistryExplorer软件来查看加载的“设备”,并从中读取其相应的参数。这就为我们修改DSDT提供了一个非常方便的参考。
经过频繁的试验,发现T410的2个EHCI设备的DSDT参数设置不正确,是造成T410黑苹果睡眠唤醒后死机(包括插入U盘死机)现象的主要原因。
我们分析一下:在Device (EHC1)和Device (EHC2)中,我们在DSDT里面一般会各添加一段Method (_DSM, 4, NotSerialized)代码,俗称“USB内建”。代码如下:
Method (_DSM, 4, NotSerialized)
{
Store (Package (0x0F)
{
"device-id",
Buffer (0x04)
{
0x34, 0x3A, 0x00, 0x00
},
"AAPL,clock-id",
Buffer (One)
{
0x0A
},
"built-in",
Buffer (One)
{
0x00
},
"device_type",
Buffer (0x05)
{
"EHCI"
},
"AAPL,current-available",
0x04B0,
"AAPL,current-extra",
0x02BC,
"AAPL,current-in-sleep",
0x03E8,
Buffer (One)
{
0x00
}
}, Local0)
DTGP (Arg0, Arg1, Arg2, Arg3, RefOf (Local0))
Return (Local0)
}
很多人就直接复制粘贴而不做任何修改。虽然看起来运行正常,而实际上给睡眠唤醒之后的死机、以及唤醒之后插入U盘的死机造成了很大的隐患!
从IORegistryExplorer软件中,我们实际上可以看到EHC1和EHC2下还有一些未被用到的USB2.0端口(如:EHCI Root Hub Simulation@1D)。这些被红线框起来的参数是系统自动读取的,也就是说端口的参数本来就是这些值。
http://static.pb.pbcdn.com/data/attachment/album/201301/15/1431353b77dwjidyoelto5.jpg
在上图,可以看到很多参数都是上面的DSDT代码中没有的,如"AAPL,device-internal","AAPL,max-port-current-in-sleep","AAPL,standard-port-current-in-sleep"。我们还会发现以上DSDT代码中的三个AAPL的值也与之不同,也就是说DSDT中的参数不正确!
同时,在WINDOWS中,我们使用AIDA64软件生成一个硬件的报告,从该报告中可以查到T410的EHC1和EHC2的设备ID分别是0x3B34和0x3B3C。因此,我们需要对以上代码进行修正。
其中EHC1部分修正之后如下:
Method (_DSM, 4, NotSerialized)
{
Store (Package (0x13)
{
"device-id",
Buffer (0x04)
{
0x34, 0x3B, 0x00, 0x00
},
"AAPL,clock-id",
Buffer (One)
{
0x01
},
"device_type",
Buffer (0x05)
{
"EHCI"
},
"AAPL,current-available",
0x05DC,
"AAPL,current-extra",
0x04B0,
"AAPL,current-extra-in-sleep",
0x03E8,
"AAPL,device-internal",
0x02,
"AAPL,max-port-current-in-sleep",
0x3E8,
"AAPL,standard-port-current-in-sleep",
0X1F4,
Buffer (One)
{
0x00
}
}, Local0)
DTGP (Arg0, Arg1, Arg2, Arg3, RefOf (Local0))
Return (Local0)
}
而EHC2部分修正之后为:
Method (_DSM, 4, NotSerialized)
{
Store (Package (0x13)
{
"device-id",
Buffer (0x04)
{
0x3C, 0x3B, 0x00, 0x00
},
"AAPL,clock-id",
Buffer (One)
{
0x02
},
"device_type",
Buffer (0x05)
{
"EHCI"
},
"AAPL,current-available",
0x05DC,
"AAPL,current-extra",
0x04B0,
"AAPL,current-extra-in-sleep",
0x03E8,
"AAPL,device-internal",
0x02,
"AAPL,max-port-current-in-sleep",
0x3E8,
"AAPL,standard-port-current-in-sleep",
0X1F4,
Buffer (One)
{
0x00
}
}, Local0)
DTGP (Arg0, Arg1, Arg2, Arg3, RefOf (Local0))
Return (Local0)
}
至此,我们应该来说比较完美地解决了EHC1和EHC2两个设备的硬件参数在DSDT中的相应代码修改。至少在今天一整天的多次睡眠唤醒后,插入/拔出U盘(有读写动作)、同时使用USB打印机,未发现死机现象。
二楼将补充关于IRQ、FIREWIRE提示、SMBUS、有线网卡内建、SATA内建、Fn键、小太阳、合盖睡眠、按电源键睡眠、关机断电等DSDT修改。
至于新版DSDT,我将继续测试几天之后,如果相对稳定了,就上传。
特别感谢LeoGray坛友提供的“插入U盘死机”信息!!
=====================================
新版T410的DSDT在此下载。此DSDT基于1.44版白名单BIOS,并精简掉了Device (LPT)和Device (ECP),因为即使有这2段代码也加载不了。从理论上来说,不会影响刷其他版本BIOS的机器。请使用后反馈状况!
该DSDT支持变色龙与CLOVER启动!!!
关于CLOVER引导的方法,见https://bbs.pcbeta.com/viewthread-1268481-1-1.html
另,本DSDT无论使用变色龙、或者使用CLOVER引导启动,都需要启动这两个引导的显卡自动侦测功能。即:变色龙的GraphicsEnabler=Yes,CLOVER的GraphicsInjector=Yes,【适用于NVS3100M显卡】。
我的使用情况:
1)启动运行正常;
2)自动睡眠唤醒正常;
3)合盖睡眠唤醒正常;
4)Fn+F4睡眠唤醒正常;
5)唤醒后插入U盘读写正常;
6)连续多种睡眠唤醒正常;
7)长时间睡眠唤醒正常;
注:我的机器型号是T410-2522-RT8,NVS3100M独显。若是集显或者双显卡的T410,建议参考本贴为主。
补充关于IRQ、FIREWIRE提示、SMBUS、有线网卡内建、SATA内建、Fn键、小太阳、睡眠等
本帖最后由 gcafrk 于 2013-1-27 23:27 编辑补充关于IRQ、FIREWIRE提示、SMBUS、有线网卡内建、SATA内建、Fn键、小太阳、按电源键睡眠、关机断电、指纹驱动等DSDT修改。
一、关于IRQ
1)HPET的IRQ。由于i5-520m是双核四线程CPU,它需要4个IRQ。我们参考DSDTSE或者DSDT Editor中的说明,添加2个IRQ(0和8),同时也参考其他帖子,再为其增加2个IRQ(11和15),则代码变成:
Device (HPET)
{
Name (_HID, EisaId ("PNP0103"))
Method (_STA, 0, NotSerialized)
{
Return (0x0F)
}
Name (_CRS, ResourceTemplate ()
{
IRQNoFlags ()
{0}
IRQNoFlags ()
{8}
IRQNoFlags ()
{11}
IRQNoFlags ()
{15}
Memory32Fixed (ReadOnly,
0xFED00000, // Address Base
0x00000400, // Address Length
)
})
}
2)RTC的IRQ,需要删除。删除之后的代码如下:
Device (RTC)
{
Name (_HID, EisaId ("PNP0B00"))
Name (_CRS, ResourceTemplate ()
{
IO (Decode16,
0x0070, // Range Minimum
0x0070, // Range Maximum
0x01, // Alignment
0x02, // Length
)
})
}
3)TIMR的IRQ,需要删除。删除之后的代码如下:
Device (TIMR)
{
Name (_HID, EisaId ("PNP0100"))
Name (_CRS, ResourceTemplate ()
{
IO (Decode16,
0x0040, // Range Minimum
0x0040, // Range Maximum
0x01, // Alignment
0x04, // Length
)
})
}
二、Firewire(火线)启动日志FireWire runtime power conservation disabled去除:
1)在IORegistryExplorer中查询到火线Firewire的位置:在EXP5。因此,在DSDT的Device (EXP5)的Method (_PRT, 0, NotSerialized)之前,添加以下代码:
Device (FRWR)
{
Name (_ADR, 0x03)
Name (_GPE, 0x1A)
Method (_DSM, 4, NotSerialized)
{
Store (Package (0x02)
{
"fwhub",
Buffer (0x04)
{
0x00, 0x00, 0x00, 0x00
}
}, Local0)
DTGP (Arg0, Arg1, Arg2, Arg3, RefOf (Local0))
Return (Local0)
}
}
2)在Scope (_GPE)中添加以下代码:
Method (_L1A, 0, NotSerialized)
{
Notify (\_SB.PCI0.EXP5.FRWR, Zero)
}
三、SMBUS:在T410的DSDT原始代码中,SMBUS只有以下这些:
Device (SMBU)
{
Name (_ADR, 0x001F0003)
Name (_S3D, 0x03)
Name (RID, 0x00)
}
我们需要将其改成:
Device (SMBU)
{
Name (_ADR, 0x001F0003)
Name (_S3D, 0x03)
Name (RID, Zero)
Device (BUS0)
{
Name (_CID, "smbus")
Name (_ADR, Zero)
Device (DVL0)
{
Name (_ADR, 0x57)
Name (_CID, "diagsvault")
}
}
Method (_DSM, 4, NotSerialized)
{
Store (Package (0x04)
{
"name",
Buffer (0x0D)
{
"pci8086,3a30"
},
"device-id",
Buffer (0x04)
{
0x30, 0x3A, 0x00, 0x00
}
}, Local0)
DTGP (Arg0, Arg1, Arg2, Arg3, RefOf (Local0))
Return (Local0)
}
}
四、有线网卡内建:
在Device (IGBE)中添加有线网卡内建代码,最终Device (IGBE)如下:
Device (IGBE)
{
Name (_ADR, 0x00190000)
Name (_S3D, 0x03)
Name (RID, Zero)
Name (_PRW, Package (0x02)
{
0x0D,
0x04
})
Method (_DSM, 4, NotSerialized)
{
Store (Package (0x06)
{
"built-in",
Buffer (One)
{
0x01
},
"device_type",
Buffer (0x09)
{
"ethernet"
},
"name",
Buffer (0x16)
{
"Intel 82577LM Gigabit"
}
}, Local0)
DTGP (Arg0, Arg1, Arg2, Arg3, RefOf (Local0))
Return (Local0)
}
}
五、SATA内建:
* T410原始DSDT的SATA代码并未带有内建代码,因此,为Device (SAT1)和Device (SAT2)其添加以下部分:
Method (_DSM, 4, NotSerialized)
{
Store (Package (0x02)
{
"device-id",
Buffer (0x04)
{
0x2F, 0x3B, 0x00, 0x00
}
}, Local0)
DTGP (Arg0, Arg1, Arg2, Arg3, RefOf (Local0))
Return (Local0)
}
六、添加Fn键功能:
* 找到Device (KBD),在其中添加:
Method (_DSM, 4, NotSerialized)
{
Store (Package (0x02)
{
"AAPL,has-embedded-fn-keys",
Buffer (0x04)
{
0x01, 0x00, 0x00, 0x00
}
}, Local0)
DTGP (Arg0, Arg1, Arg2, Arg3, RefOf (Local0))
Return (Local0)
}
七、关于小太阳:
*T410用的是ScrLk和Pause两个按键来调节显示器的亮度。需要在Scope (_SB)中添加以下代码,我添加的位置是在Method (_INI, 0, NotSerialized)之后,在Device (LNKA)之前:
Device (PNLF)
{
Name (_HID, EisaId ("APP0002"))
Name (_CID, "backlight")
Name (_UID, 0x0A)
Name (_STA, 0x0B)
}
八、按电源键睡眠:
* 在Device (SLPB)之前添加:
Device (PWRB)
{
Name (_CID, EisaId ("PNP0C0C"))
Name (_UID, 0xAA)
Method (_STA, 0, NotSerialized)
{
Return (0x0B)
}
}
九、关机断电:
在Method (_PTS, 1, NotSerialized)之前,添加以下代码:【注意第一行的0x1030是T410专用的,相关资料看我的日志】
OperationRegion (PMRS, SystemIO, 0x1030, 0x13)
Field (PMRS, ByteAcc, NoLock, Preserve)
{
, 4,
SLPE, 1
}
同时,在Method (_PTS, 1, NotSerialized)中的If (LEqual (Arg0, 0x05))里面添加非常关键的两行:
Store (Zero, SLPE)
Sleep (0x10)
之后,完整的代码如下: If (LEqual (Arg0, 0x05))
{
TRAP ()
TPHY (0x02)
AWON (0x05)
Store (Zero, SLPE)
Sleep (0x10)
}
十、添加指纹设备:搜索:FPU,在代码:
Name (_HID, EisaId ("PNP0C04"))
Name (_CRS, ResourceTemplate ()
{
IO (Decode16,
0x00F0, // Range Minimum
0x00F0, // Range Maximum
0x02, // Alignment
0x02, // Length
)
IRQNoFlags ()
{13}
})下面加入内建USB代码:
Method (_DSM, 4, NotSerialized)
{
Store (Package (0x02)
{
"device-id",
Buffer (0x04)
{
0x16, 0x20, 0x00, 0x00
}
}, Local0)
DTGP (Arg0, Arg1, Arg2, Arg3, RefOf (Local0))
Return (Local0)
}
本帖最后由 gcafrk 于 2013-2-17 22:17 编辑
IORegistryExplorer中看不到LPT和ECP设备,果断删除DSDT中的Device (LPT)和Device (ECP)。试验效果不错,不影响。决定T410的新版DSDT可以删除这两个Device。
* 关于显卡代码,我只在Device (PEG)设备下的Device (VID)中添加了以下代码,然后启用变色龙的GraphicsEnabler=yes。
Method (_DSM, 4, NotSerialized)
{
Store (Package (0x06)
{
"@0,built-in",
Buffer (0x04)
{
0x01, 0x00, 0x00, 0x00
},
"@0,backlight-control",
Buffer (0x04)
{
0x01, 0x00, 0x00, 0x00
},
"@0,pwm-info",
Buffer (0x14)
{
/* 0000 */ 0x01, 0x14, 0x00, 0x64, 0xA8, 0x61, 0x00, 0x00,
/* 0008 */ 0x08, 0x52, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
/* 0010 */ 0x00, 0x04, 0x00, 0x00
}
}, Local0)
DTGP (Arg0, Arg1, Arg2, Arg3, RefOf (Local0))
Return (Local0)
}有人可能需要更多更长的显卡代码,这里就暂时不做更多讨论了。
* 关于原生CPU电源管理AppleLPC,正确代码如下:
Device (LPC)
{
Name (_ADR, 0x001F0000)
Method (_DSM, 4, NotSerialized)
{
Store (Package (0x02)
{
"device-id",
Buffer (0x04)
{
0x07, 0x3B, 0x00, 0x00 //3B07是Intel mobile 5/3400
}
}, Local0)
DTGP (Arg0, Arg1, Arg2, Arg3, RefOf (Local0))
Return (Local0)
}
关于这个3B07,可以在MAC中用System Info来查看,T410的是"Mobile 5 Serials Chipset LPC Interface Controller"。其他主板也类似的思路。修改DSDT之后,还需要在AppleLPC.kext中添加3B07这个ID,或者使用我修改过的的FakeSMC.kext。这样子才能加载AppleLPC,达到降温的效果。
LZ牛人…………顶顶顶顶 牛叉啊,挖大发发发疯 本帖最后由 gcafrk 于 2013-1-15 10:00 编辑
Jan 14 20:26:01 localhost bootlog: BOOT_TIME 1358166361 0 (启动)
Jan 14 21:14:49 MacBook-Pro kernel: Wake reason = SLPB LID(睡眠唤醒)
Jan 14 23:09:05 MacBook-Pro kernel: Wake reason = SLPB LID(睡眠唤醒)
Jan 15 09:37:10 MacBook-Pro kernel: Wake reason = SLPB LID(睡眠唤醒)
这期间连续合盖睡眠+唤醒+插入U盘使用+USB打印。
目前正常使用。 感谢楼主的分享,能否分享一下你的dsdt? gcafrk 发表于 2013-1-15 09:59 static/image/common/back.gif
Jan 14 20:26:01 localhost bootlog: BOOT_TIME 1358166361 0 (启动)
Jan 14 21:14:49 MacBook-Pro k ...
这就试试看,目前我在唤醒后不插USB的情况下,唤醒基本完美。死机的情况很少很少。
有的时候都忘记现在使用是唤醒后的机器了。
可惜现在电脑上没win,没办法看信息,还得抽空折腾个win。要是能在mac下完成就好了。 arctic520 发表于 2013-1-15 11:51 static/image/common/back.gif
感谢楼主的分享,能否分享一下你的dsdt?
我不是呵楼主一个机型,只是想看下你的dsdt代码!!要不你发我邮箱
806039704@qq.com 给个帖子给你参考下https://bbs.pcbeta.com/viewthread-943580-1-1.html 恩 谢谢啦 先拿来看看 不错................... 麻烦你帮我看下i3-370m IRQ是 0 8 还有什么? arctic520 发表于 2013-1-15 15:01 static/image/common/back.gif
麻烦你帮我看下i3-370m IRQ是 0 8 还有什么?
好,非常感谢! dsdt没摆平的usb问题,我用的<key>USBBusFix</key>
<string>Yes</string>
搞定的。 无条件支持楼主 和各位大神 么么哒 现在像楼主这样无私奉献的人越来越少了,我们向楼主学习,期代DSDT稳定后出现 LZ 我添加了
这几行代码 会出错
: Method (_L1A, 0, NotSerialized)
{
Notify (\_SB.PCI0.EXP5.FRWR, Zero)
}
说是object 没有结束!!!怎么解决? nothing_typ 发表于 2013-1-15 16:58 static/image/common/back.gif
LZ 我添加了
这几行代码 会出错
: Method (_L1A, 0, NotSerialized)
不会啊,我这里加了没出错,是不是加错地方了?Device (FRWR)加了没? 本帖最后由 nothing_typ 于 2013-1-15 17:22 编辑
gcafrk 发表于 2013-1-15 17:10 static/image/common/back.gif
不会啊,我这里加了没出错,是不是加错地方了?Device (FRWR)加了没?
加了,我附上我的DSDT 帮我看看把。