<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>https://wiki.mainlining.org/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Knuxify</id>
	<title>Mainlining Wiki - User contributions [en]</title>
	<link rel="self" type="application/atom+xml" href="https://wiki.mainlining.org/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Knuxify"/>
	<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/wiki/Special:Contributions/Knuxify"/>
	<updated>2026-04-25T11:09:26Z</updated>
	<subtitle>User contributions</subtitle>
	<generator>MediaWiki 1.43.0</generator>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=110</id>
		<title>User:Knuxify/Draft:Qualcomm/Adding a new SoC to mainline Linux</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=110"/>
		<updated>2026-02-02T19:14:19Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: /* Finding information about your SoC */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Subpage of|Qualcomm}}&lt;br /&gt;
{{Work-in-progress page|note=Currently in the middle of finding this out in real time :)}}&lt;br /&gt;
&lt;br /&gt;
This guide will cover the process of adding support for a recent (~2020 or newer, todo?) Qualcomm SoC into mainline Linux. Most of the information contained within is also applicable to older chips, though more manual effort may be needed to get these to run. &amp;lt;!--For the U-Boot guide, see TODO.--&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This guide was tested with the SM7435. Some details might be different for other SoCs. If you have any hints, please contribute!&lt;br /&gt;
&lt;br /&gt;
== High-level overview ==&lt;br /&gt;
&lt;br /&gt;
{{todo|Some of this will have to be moved out to the top-level Qualcomm page}}&lt;br /&gt;
&lt;br /&gt;
The basic components of a Qualcomm SoC are:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;GCC&#039;&#039;&#039;, or &#039;&#039;Global Clock Controller&#039;&#039;; as the name suggests, it is the primary clock controller for most components.&lt;br /&gt;
* The other clock controllers: &#039;&#039;&#039;CAMCC&#039;&#039;&#039;, &#039;&#039;&#039;DISPCC&#039;&#039;&#039;, &#039;&#039;&#039;GPUCC&#039;&#039;&#039; and &#039;&#039;&#039;VIDEOCC&#039;&#039;&#039;.&lt;br /&gt;
* The &#039;&#039;&#039;RPM&#039;&#039;&#039;, or &#039;&#039;Resource and Power Manager&#039;&#039; (&#039;&#039;&#039;RPMH&#039;&#039;&#039; or RPM &#039;&#039;Hardened&#039;&#039; in SDM845 and later); todo explanation from [https://wiki.postmarketos.org/wiki/Qualcomm_Glossary qcom glossary].&lt;br /&gt;
** Under the RPM is the &#039;&#039;&#039;RPM(H)CC&#039;&#039;&#039; (&#039;&#039;RPM clock controller&#039;&#039;) and &#039;&#039;&#039;RPM(H)PD&#039;&#039;&#039; (&#039;&#039;RPM power domains&#039;&#039;).&lt;br /&gt;
* &#039;&#039;&#039;QUP&#039;&#039;&#039;, or &#039;&#039;Qualcomm Universal Peripheral&#039;&#039;; the part of the SoC that provides I2C or SPI busses, as well as UART.&lt;br /&gt;
* &#039;&#039;&#039;TLMM&#039;&#039;&#039; (&#039;&#039;Top Level Mode Multiplexer&#039;&#039;); provides pinmux and GPIO pins.&lt;br /&gt;
* Many &#039;&#039;&#039;NOC&#039;&#039;&#039; interconnects (&#039;&#039;Network on Chip&#039;&#039;).&lt;br /&gt;
* A timer and an interrupt controller, both standard ARM parts.&lt;br /&gt;
&lt;br /&gt;
These are just the most low-level components; from there, we can move on to the higher-level ones:&lt;br /&gt;
&lt;br /&gt;
* Thermal monitoring sensor&lt;br /&gt;
* USB host controller and PHY&lt;br /&gt;
* Display controller and DSI PHY&lt;br /&gt;
* GPU&lt;br /&gt;
* etc.&lt;br /&gt;
&lt;br /&gt;
This page will touch on mainline porting of most of these parts.&lt;br /&gt;
&lt;br /&gt;
== Finding information about your SoC ==&lt;br /&gt;
&lt;br /&gt;
In order to begin mainlining your SoC, you need to have the following bits of information:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;codenames&#039;&#039;&#039; of the SoC. Qualcomm SoCs appear to have two codenames&amp;lt;ref&amp;gt;The names of these codenames have been sourced from [https://wiki.postmarketos.org/wiki/Qualcomm_Snapdragon_8_Gen_1/8%2B_Gen_1/7%2B_Gen_2_(SM8450/SM8475/SM7475) the postmarketOS wiki page for the Snapdragon 8 Gen 1], not sure where that is sourced from.&amp;lt;/ref&amp;gt;:&lt;br /&gt;
** &#039;&#039;&#039;Board codename&#039;&#039;&#039; (&amp;quot;DTS nickname&amp;quot;?) - you&#039;ll find it in the driver names on the device, as well as in the main compatible string of the devicetree. This is what&#039;s used across most of the downstream kernel.&lt;br /&gt;
** &#039;&#039;&#039;Platform codename&#039;&#039;&#039; - presumably shared between multiple SoCs from the same family.&lt;br /&gt;
** Since SM7635 (&amp;quot;Volcano&amp;quot;/&amp;quot;Milos&amp;quot;) getting upstreamed, Qualcomm appears to have changed their policy around driver/compatible naming in mainline and now expects developers to use the platform codename instead of the model number&amp;lt;ref&amp;gt;https://lore.kernel.org/lkml/888a7598-38d9-4640-9823-2b073da006f4@kernel.org/&amp;lt;/ref&amp;gt;. If you&#039;re unsure of the platform codename for your device, you can send the Qualcomm folks an email and ask them directly&amp;lt;ref&amp;gt;I ended up getting [https://lore.kernel.org/lkml/c379aad4-96f6-4134-8b90-0f1eec8001a3@oss.qualcomm.com/ a public reply to my query for SM7435].&amp;lt;/ref&amp;gt;, or just use the model name for now and let them correct you (as was done in the Milos case).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;downstream kernel&#039;&#039;&#039;; preferably the one for your device, but you can also use the kernel from another device with the same SoC, or - as a last resort - any kernel with the relevant SoC drivers (hint: search by downstream codename).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;&amp;lt;code&amp;gt;qcom_proprietary_devicetree&amp;lt;/code&amp;gt;&#039;&#039;&#039; or similar repo with the DTSI source files (because they&#039;re not in the kernel repo for whatever reason...). Search for &amp;lt;code&amp;gt;(downstream codename).dtsi&amp;lt;/code&amp;gt; on GitHub and you&#039;ll find the right repository eventually.&lt;br /&gt;
* An &#039;&#039;&#039;extracted DTB from your device&#039;&#039;&#039;. Dump this from a running device using FDT (todo: instructions, would probably be good on a generic page, maybe subpage of [[Devicetree]])?&lt;br /&gt;
* Find a similar SoC that is already supported. Usually flagship SoCs are available in mainline; try to find a flagship from around the same time as the SoC you&#039;re mainlining. Find its DTSIs as well; then you can compare the differences between downstream and mainline for the upstreamed SoC, and correlate them with differences in your SoC. You&#039;ll also be able to check the other SoC&#039;s drivers and use them as a base for your own drivers.&lt;br /&gt;
&lt;br /&gt;
== Adding the DTSI ==&lt;br /&gt;
&lt;br /&gt;
todo&lt;br /&gt;
&lt;br /&gt;
== Porting individual parts ==&lt;br /&gt;
&lt;br /&gt;
=== Clock controllers ===&lt;br /&gt;
&lt;br /&gt;
On recent Qualcomm SoCs, the downstream kernel uses the mainline Qualcomm clock driver with only &#039;&#039;some&#039;&#039; vendor-specific quirks. This means that the clock drivers and their relevant headers can pretty much be copied verbatim from downstream, with some slight modifications.&lt;br /&gt;
&lt;br /&gt;
First, create the &#039;&#039;&#039;GCC&#039;&#039;&#039; driver. Open &amp;lt;code&amp;gt;driver/clk/qcom/Kconfig&amp;lt;/code&amp;gt; and add the relevant Kconfig option for your SoC (remember to keep it ordered alphabetically):&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;kconfig&amp;quot;&amp;gt;&lt;br /&gt;
config SM_GCC_xxxx&lt;br /&gt;
	tristate &amp;quot;SMxxxx Global Clock Controller&amp;quot;&lt;br /&gt;
	depends on ARM64 || COMPILE_TEST&lt;br /&gt;
	select QCOM_GDSC&lt;br /&gt;
	help&lt;br /&gt;
	  Support for the global clock controller on SMxxxx devices.&lt;br /&gt;
	  Say Y if you want to use peripheral devices such as UART,&lt;br /&gt;
	  SPI, I2C, USB, SD/UFS, PCIe etc.&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/Makefile&amp;lt;/code&amp;gt; and add the relevant entry:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;makefile&amp;quot;&amp;gt;&lt;br /&gt;
obj-$(CONFIG_SM_GCC_xxxx) += gcc-smXXXX.o&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/gcc-smXXXX.c&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Paste the initialization code from another GCC driver (&amp;lt;syntaxhighlight inline lang=&amp;quot;c&amp;quot;&amp;gt;static struct platform_driver gcc_smXXXX_driver&amp;lt;/syntaxhighlight&amp;gt; and onwards.)&lt;br /&gt;
&lt;br /&gt;
== Porting the PMIC(s) ==&lt;br /&gt;
&lt;br /&gt;
Qualcomm devices use &#039;&#039;multiple&#039;&#039; PMICs for different purposes. Often, the PMIC is paired with an SoC or series of SoCs.&lt;br /&gt;
&lt;br /&gt;
== References ==&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=109</id>
		<title>User:Knuxify/Draft:Qualcomm/Adding a new SoC to mainline Linux</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=109"/>
		<updated>2026-02-02T19:12:36Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: /* Finding information about your SoC */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Subpage of|Qualcomm}}&lt;br /&gt;
{{Work-in-progress page|note=Currently in the middle of finding this out in real time :)}}&lt;br /&gt;
&lt;br /&gt;
This guide will cover the process of adding support for a recent (~2020 or newer, todo?) Qualcomm SoC into mainline Linux. Most of the information contained within is also applicable to older chips, though more manual effort may be needed to get these to run. &amp;lt;!--For the U-Boot guide, see TODO.--&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This guide was tested with the SM7435. Some details might be different for other SoCs. If you have any hints, please contribute!&lt;br /&gt;
&lt;br /&gt;
== High-level overview ==&lt;br /&gt;
&lt;br /&gt;
{{todo|Some of this will have to be moved out to the top-level Qualcomm page}}&lt;br /&gt;
&lt;br /&gt;
The basic components of a Qualcomm SoC are:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;GCC&#039;&#039;&#039;, or &#039;&#039;Global Clock Controller&#039;&#039;; as the name suggests, it is the primary clock controller for most components.&lt;br /&gt;
* The other clock controllers: &#039;&#039;&#039;CAMCC&#039;&#039;&#039;, &#039;&#039;&#039;DISPCC&#039;&#039;&#039;, &#039;&#039;&#039;GPUCC&#039;&#039;&#039; and &#039;&#039;&#039;VIDEOCC&#039;&#039;&#039;.&lt;br /&gt;
* The &#039;&#039;&#039;RPM&#039;&#039;&#039;, or &#039;&#039;Resource and Power Manager&#039;&#039; (&#039;&#039;&#039;RPMH&#039;&#039;&#039; or RPM &#039;&#039;Hardened&#039;&#039; in SDM845 and later); todo explanation from [https://wiki.postmarketos.org/wiki/Qualcomm_Glossary qcom glossary].&lt;br /&gt;
** Under the RPM is the &#039;&#039;&#039;RPM(H)CC&#039;&#039;&#039; (&#039;&#039;RPM clock controller&#039;&#039;) and &#039;&#039;&#039;RPM(H)PD&#039;&#039;&#039; (&#039;&#039;RPM power domains&#039;&#039;).&lt;br /&gt;
* &#039;&#039;&#039;QUP&#039;&#039;&#039;, or &#039;&#039;Qualcomm Universal Peripheral&#039;&#039;; the part of the SoC that provides I2C or SPI busses, as well as UART.&lt;br /&gt;
* &#039;&#039;&#039;TLMM&#039;&#039;&#039; (&#039;&#039;Top Level Mode Multiplexer&#039;&#039;); provides pinmux and GPIO pins.&lt;br /&gt;
* Many &#039;&#039;&#039;NOC&#039;&#039;&#039; interconnects (&#039;&#039;Network on Chip&#039;&#039;).&lt;br /&gt;
* A timer and an interrupt controller, both standard ARM parts.&lt;br /&gt;
&lt;br /&gt;
These are just the most low-level components; from there, we can move on to the higher-level ones:&lt;br /&gt;
&lt;br /&gt;
* Thermal monitoring sensor&lt;br /&gt;
* USB host controller and PHY&lt;br /&gt;
* Display controller and DSI PHY&lt;br /&gt;
* GPU&lt;br /&gt;
* etc.&lt;br /&gt;
&lt;br /&gt;
This page will touch on mainline porting of most of these parts.&lt;br /&gt;
&lt;br /&gt;
== Finding information about your SoC ==&lt;br /&gt;
&lt;br /&gt;
In order to begin mainlining your SoC, you need to have the following bits of information:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;codenames&#039;&#039;&#039; of the SoC. Qualcomm SoCs appear to have two codenames&amp;lt;ref&amp;gt;The names of these codenames have been sourced from [https://wiki.postmarketos.org/wiki/Qualcomm_Snapdragon_8_Gen_1/8%2B_Gen_1/7%2B_Gen_2_(SM8450/SM8475/SM7475) the postmarketOS wiki page for the Snapdragon 8 Gen 1], not sure where that is sourced from.&amp;lt;/ref&amp;gt;:&lt;br /&gt;
** &#039;&#039;&#039;Board codename&#039;&#039;&#039; (&amp;quot;DTS nickname&amp;quot;?) - you&#039;ll find it in the driver names on the device, as well as in the main compatible string of the devicetree. This is what&#039;s used across most of the downstream kernel.&lt;br /&gt;
** &#039;&#039;&#039;Platform codename&#039;&#039;&#039; - presumably shared between multiple SoCs from the same family.&lt;br /&gt;
** Since SM7635 (&amp;quot;Volcano&amp;quot;/&amp;quot;Milos&amp;quot;), Qualcomm has changed their policy around driver/compatible naming in mainline and now expects developers to use the platform codename instead&amp;lt;ref&amp;gt;https://lore.kernel.org/lkml/888a7598-38d9-4640-9823-2b073da006f4@kernel.org/&amp;lt;/ref&amp;gt;. If you&#039;re unsure of the platform codename for your device, you can send the Qualcomm folks an email and ask them directly&amp;lt;ref&amp;gt;I ended up getting [https://lore.kernel.org/lkml/c379aad4-96f6-4134-8b90-0f1eec8001a3@oss.qualcomm.com/ a public reply to my query for SM7435].&amp;lt;/ref&amp;gt;, or just use the model name for now and let them correct you (as was done in the Milos case).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;downstream kernel&#039;&#039;&#039;; preferably the one for your device, but you can also use the kernel from another device with the same SoC, or - as a last resort - any kernel with the relevant SoC drivers (hint: search by downstream codename).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;&amp;lt;code&amp;gt;qcom_proprietary_devicetree&amp;lt;/code&amp;gt;&#039;&#039;&#039; or similar repo with the DTSI source files (because they&#039;re not in the kernel repo for whatever reason...). Search for &amp;lt;code&amp;gt;(downstream codename).dtsi&amp;lt;/code&amp;gt; on GitHub and you&#039;ll find the right repository eventually.&lt;br /&gt;
* An &#039;&#039;&#039;extracted DTB from your device&#039;&#039;&#039;. Dump this from a running device using FDT (todo: instructions, would probably be good on a generic page, maybe subpage of [[Devicetree]])?&lt;br /&gt;
* Find a similar SoC that is already supported. Usually flagship SoCs are available in mainline; try to find a flagship from around the same time as the SoC you&#039;re mainlining. Find its DTSIs as well; then you can compare the differences between downstream and mainline for the upstreamed SoC, and correlate them with differences in your SoC. You&#039;ll also be able to check the other SoC&#039;s drivers and use them as a base for your own drivers.&lt;br /&gt;
&lt;br /&gt;
== Adding the DTSI ==&lt;br /&gt;
&lt;br /&gt;
todo&lt;br /&gt;
&lt;br /&gt;
== Porting individual parts ==&lt;br /&gt;
&lt;br /&gt;
=== Clock controllers ===&lt;br /&gt;
&lt;br /&gt;
On recent Qualcomm SoCs, the downstream kernel uses the mainline Qualcomm clock driver with only &#039;&#039;some&#039;&#039; vendor-specific quirks. This means that the clock drivers and their relevant headers can pretty much be copied verbatim from downstream, with some slight modifications.&lt;br /&gt;
&lt;br /&gt;
First, create the &#039;&#039;&#039;GCC&#039;&#039;&#039; driver. Open &amp;lt;code&amp;gt;driver/clk/qcom/Kconfig&amp;lt;/code&amp;gt; and add the relevant Kconfig option for your SoC (remember to keep it ordered alphabetically):&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;kconfig&amp;quot;&amp;gt;&lt;br /&gt;
config SM_GCC_xxxx&lt;br /&gt;
	tristate &amp;quot;SMxxxx Global Clock Controller&amp;quot;&lt;br /&gt;
	depends on ARM64 || COMPILE_TEST&lt;br /&gt;
	select QCOM_GDSC&lt;br /&gt;
	help&lt;br /&gt;
	  Support for the global clock controller on SMxxxx devices.&lt;br /&gt;
	  Say Y if you want to use peripheral devices such as UART,&lt;br /&gt;
	  SPI, I2C, USB, SD/UFS, PCIe etc.&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/Makefile&amp;lt;/code&amp;gt; and add the relevant entry:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;makefile&amp;quot;&amp;gt;&lt;br /&gt;
obj-$(CONFIG_SM_GCC_xxxx) += gcc-smXXXX.o&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/gcc-smXXXX.c&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Paste the initialization code from another GCC driver (&amp;lt;syntaxhighlight inline lang=&amp;quot;c&amp;quot;&amp;gt;static struct platform_driver gcc_smXXXX_driver&amp;lt;/syntaxhighlight&amp;gt; and onwards.)&lt;br /&gt;
&lt;br /&gt;
== Porting the PMIC(s) ==&lt;br /&gt;
&lt;br /&gt;
Qualcomm devices use &#039;&#039;multiple&#039;&#039; PMICs for different purposes. Often, the PMIC is paired with an SoC or series of SoCs.&lt;br /&gt;
&lt;br /&gt;
== References ==&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=108</id>
		<title>User:Knuxify/Draft:Qualcomm/Adding a new SoC to mainline Linux</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=108"/>
		<updated>2026-02-02T19:11:54Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: /* Finding information about your SoC */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Subpage of|Qualcomm}}&lt;br /&gt;
{{Work-in-progress page|note=Currently in the middle of finding this out in real time :)}}&lt;br /&gt;
&lt;br /&gt;
This guide will cover the process of adding support for a recent (~2020 or newer, todo?) Qualcomm SoC into mainline Linux. Most of the information contained within is also applicable to older chips, though more manual effort may be needed to get these to run. &amp;lt;!--For the U-Boot guide, see TODO.--&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This guide was tested with the SM7435. Some details might be different for other SoCs. If you have any hints, please contribute!&lt;br /&gt;
&lt;br /&gt;
== High-level overview ==&lt;br /&gt;
&lt;br /&gt;
{{todo|Some of this will have to be moved out to the top-level Qualcomm page}}&lt;br /&gt;
&lt;br /&gt;
The basic components of a Qualcomm SoC are:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;GCC&#039;&#039;&#039;, or &#039;&#039;Global Clock Controller&#039;&#039;; as the name suggests, it is the primary clock controller for most components.&lt;br /&gt;
* The other clock controllers: &#039;&#039;&#039;CAMCC&#039;&#039;&#039;, &#039;&#039;&#039;DISPCC&#039;&#039;&#039;, &#039;&#039;&#039;GPUCC&#039;&#039;&#039; and &#039;&#039;&#039;VIDEOCC&#039;&#039;&#039;.&lt;br /&gt;
* The &#039;&#039;&#039;RPM&#039;&#039;&#039;, or &#039;&#039;Resource and Power Manager&#039;&#039; (&#039;&#039;&#039;RPMH&#039;&#039;&#039; or RPM &#039;&#039;Hardened&#039;&#039; in SDM845 and later); todo explanation from [https://wiki.postmarketos.org/wiki/Qualcomm_Glossary qcom glossary].&lt;br /&gt;
** Under the RPM is the &#039;&#039;&#039;RPM(H)CC&#039;&#039;&#039; (&#039;&#039;RPM clock controller&#039;&#039;) and &#039;&#039;&#039;RPM(H)PD&#039;&#039;&#039; (&#039;&#039;RPM power domains&#039;&#039;).&lt;br /&gt;
* &#039;&#039;&#039;QUP&#039;&#039;&#039;, or &#039;&#039;Qualcomm Universal Peripheral&#039;&#039;; the part of the SoC that provides I2C or SPI busses, as well as UART.&lt;br /&gt;
* &#039;&#039;&#039;TLMM&#039;&#039;&#039; (&#039;&#039;Top Level Mode Multiplexer&#039;&#039;); provides pinmux and GPIO pins.&lt;br /&gt;
* Many &#039;&#039;&#039;NOC&#039;&#039;&#039; interconnects (&#039;&#039;Network on Chip&#039;&#039;).&lt;br /&gt;
* A timer and an interrupt controller, both standard ARM parts.&lt;br /&gt;
&lt;br /&gt;
These are just the most low-level components; from there, we can move on to the higher-level ones:&lt;br /&gt;
&lt;br /&gt;
* Thermal monitoring sensor&lt;br /&gt;
* USB host controller and PHY&lt;br /&gt;
* Display controller and DSI PHY&lt;br /&gt;
* GPU&lt;br /&gt;
* etc.&lt;br /&gt;
&lt;br /&gt;
This page will touch on mainline porting of most of these parts.&lt;br /&gt;
&lt;br /&gt;
== Finding information about your SoC ==&lt;br /&gt;
&lt;br /&gt;
In order to begin mainlining your SoC, you need to have the following bits of information:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;codenames&#039;&#039;&#039; of the SoC. Qualcomm SoCs appear to have two codenames&amp;lt;ref&amp;gt;The names of these codenames have been sourced from [https://wiki.postmarketos.org/wiki/Qualcomm_Snapdragon_8_Gen_1/8%2B_Gen_1/7%2B_Gen_2_(SM8450/SM8475/SM7475) the postmarketOS wiki page for the Snapdragon 8 Gen 1, not sure where that is sourced from.&amp;lt;/ref&amp;gt;:&lt;br /&gt;
** &#039;&#039;&#039;Board codename&#039;&#039;&#039; (&amp;quot;DTS nickname&amp;quot;?) - you&#039;ll find it in the driver names on the device, as well as in the main compatible string of the devicetree. This is what&#039;s used across most of the downstream kernel.&lt;br /&gt;
** &#039;&#039;&#039;Platform codename&#039;&#039;&#039; - presumably shared between multiple SoCs from the same family.&lt;br /&gt;
** Since SM7635 (&amp;quot;Volcano&amp;quot;/&amp;quot;Milos&amp;quot;), Qualcomm has changed their policy around driver/compatible naming in mainline and now expects developers to use the platform codename instead&amp;lt;ref&amp;gt;https://lore.kernel.org/lkml/888a7598-38d9-4640-9823-2b073da006f4@kernel.org/&amp;lt;/ref&amp;gt;. If you&#039;re unsure of the platform codename for your device, you can send the Qualcomm folks an email and ask them directly&amp;lt;ref&amp;gt;I ended up getting [https://lore.kernel.org/lkml/c379aad4-96f6-4134-8b90-0f1eec8001a3@oss.qualcomm.com/ a public reply to my query for SM7435].&amp;lt;/ref&amp;gt;, or just use the model name for now and let them correct you (as was done in the Milos case).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;downstream kernel&#039;&#039;&#039;; preferably the one for your device, but you can also use the kernel from another device with the same SoC, or - as a last resort - any kernel with the relevant SoC drivers (hint: search by downstream codename).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;&amp;lt;code&amp;gt;qcom_proprietary_devicetree&amp;lt;/code&amp;gt;&#039;&#039;&#039; or similar repo with the DTSI source files (because they&#039;re not in the kernel repo for whatever reason...). Search for &amp;lt;code&amp;gt;(downstream codename).dtsi&amp;lt;/code&amp;gt; on GitHub and you&#039;ll find the right repository eventually.&lt;br /&gt;
* An &#039;&#039;&#039;extracted DTB from your device&#039;&#039;&#039;. Dump this from a running device using FDT (todo: instructions, would probably be good on a generic page, maybe subpage of [[Devicetree]])?&lt;br /&gt;
* Find a similar SoC that is already supported. Usually flagship SoCs are available in mainline; try to find a flagship from around the same time as the SoC you&#039;re mainlining. Find its DTSIs as well; then you can compare the differences between downstream and mainline for the upstreamed SoC, and correlate them with differences in your SoC. You&#039;ll also be able to check the other SoC&#039;s drivers and use them as a base for your own drivers.&lt;br /&gt;
&lt;br /&gt;
== Adding the DTSI ==&lt;br /&gt;
&lt;br /&gt;
todo&lt;br /&gt;
&lt;br /&gt;
== Porting individual parts ==&lt;br /&gt;
&lt;br /&gt;
=== Clock controllers ===&lt;br /&gt;
&lt;br /&gt;
On recent Qualcomm SoCs, the downstream kernel uses the mainline Qualcomm clock driver with only &#039;&#039;some&#039;&#039; vendor-specific quirks. This means that the clock drivers and their relevant headers can pretty much be copied verbatim from downstream, with some slight modifications.&lt;br /&gt;
&lt;br /&gt;
First, create the &#039;&#039;&#039;GCC&#039;&#039;&#039; driver. Open &amp;lt;code&amp;gt;driver/clk/qcom/Kconfig&amp;lt;/code&amp;gt; and add the relevant Kconfig option for your SoC (remember to keep it ordered alphabetically):&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;kconfig&amp;quot;&amp;gt;&lt;br /&gt;
config SM_GCC_xxxx&lt;br /&gt;
	tristate &amp;quot;SMxxxx Global Clock Controller&amp;quot;&lt;br /&gt;
	depends on ARM64 || COMPILE_TEST&lt;br /&gt;
	select QCOM_GDSC&lt;br /&gt;
	help&lt;br /&gt;
	  Support for the global clock controller on SMxxxx devices.&lt;br /&gt;
	  Say Y if you want to use peripheral devices such as UART,&lt;br /&gt;
	  SPI, I2C, USB, SD/UFS, PCIe etc.&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/Makefile&amp;lt;/code&amp;gt; and add the relevant entry:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;makefile&amp;quot;&amp;gt;&lt;br /&gt;
obj-$(CONFIG_SM_GCC_xxxx) += gcc-smXXXX.o&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/gcc-smXXXX.c&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Paste the initialization code from another GCC driver (&amp;lt;syntaxhighlight inline lang=&amp;quot;c&amp;quot;&amp;gt;static struct platform_driver gcc_smXXXX_driver&amp;lt;/syntaxhighlight&amp;gt; and onwards.)&lt;br /&gt;
&lt;br /&gt;
== Porting the PMIC(s) ==&lt;br /&gt;
&lt;br /&gt;
Qualcomm devices use &#039;&#039;multiple&#039;&#039; PMICs for different purposes. Often, the PMIC is paired with an SoC or series of SoCs.&lt;br /&gt;
&lt;br /&gt;
== References ==&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=107</id>
		<title>User:Knuxify/Draft:Qualcomm/Adding a new SoC to mainline Linux</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=107"/>
		<updated>2026-02-02T19:11:22Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: /* Finding information about your SoC */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Subpage of|Qualcomm}}&lt;br /&gt;
{{Work-in-progress page|note=Currently in the middle of finding this out in real time :)}}&lt;br /&gt;
&lt;br /&gt;
This guide will cover the process of adding support for a recent (~2020 or newer, todo?) Qualcomm SoC into mainline Linux. Most of the information contained within is also applicable to older chips, though more manual effort may be needed to get these to run. &amp;lt;!--For the U-Boot guide, see TODO.--&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This guide was tested with the SM7435. Some details might be different for other SoCs. If you have any hints, please contribute!&lt;br /&gt;
&lt;br /&gt;
== High-level overview ==&lt;br /&gt;
&lt;br /&gt;
{{todo|Some of this will have to be moved out to the top-level Qualcomm page}}&lt;br /&gt;
&lt;br /&gt;
The basic components of a Qualcomm SoC are:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;GCC&#039;&#039;&#039;, or &#039;&#039;Global Clock Controller&#039;&#039;; as the name suggests, it is the primary clock controller for most components.&lt;br /&gt;
* The other clock controllers: &#039;&#039;&#039;CAMCC&#039;&#039;&#039;, &#039;&#039;&#039;DISPCC&#039;&#039;&#039;, &#039;&#039;&#039;GPUCC&#039;&#039;&#039; and &#039;&#039;&#039;VIDEOCC&#039;&#039;&#039;.&lt;br /&gt;
* The &#039;&#039;&#039;RPM&#039;&#039;&#039;, or &#039;&#039;Resource and Power Manager&#039;&#039; (&#039;&#039;&#039;RPMH&#039;&#039;&#039; or RPM &#039;&#039;Hardened&#039;&#039; in SDM845 and later); todo explanation from [https://wiki.postmarketos.org/wiki/Qualcomm_Glossary qcom glossary].&lt;br /&gt;
** Under the RPM is the &#039;&#039;&#039;RPM(H)CC&#039;&#039;&#039; (&#039;&#039;RPM clock controller&#039;&#039;) and &#039;&#039;&#039;RPM(H)PD&#039;&#039;&#039; (&#039;&#039;RPM power domains&#039;&#039;).&lt;br /&gt;
* &#039;&#039;&#039;QUP&#039;&#039;&#039;, or &#039;&#039;Qualcomm Universal Peripheral&#039;&#039;; the part of the SoC that provides I2C or SPI busses, as well as UART.&lt;br /&gt;
* &#039;&#039;&#039;TLMM&#039;&#039;&#039; (&#039;&#039;Top Level Mode Multiplexer&#039;&#039;); provides pinmux and GPIO pins.&lt;br /&gt;
* Many &#039;&#039;&#039;NOC&#039;&#039;&#039; interconnects (&#039;&#039;Network on Chip&#039;&#039;).&lt;br /&gt;
* A timer and an interrupt controller, both standard ARM parts.&lt;br /&gt;
&lt;br /&gt;
These are just the most low-level components; from there, we can move on to the higher-level ones:&lt;br /&gt;
&lt;br /&gt;
* Thermal monitoring sensor&lt;br /&gt;
* USB host controller and PHY&lt;br /&gt;
* Display controller and DSI PHY&lt;br /&gt;
* GPU&lt;br /&gt;
* etc.&lt;br /&gt;
&lt;br /&gt;
This page will touch on mainline porting of most of these parts.&lt;br /&gt;
&lt;br /&gt;
== Finding information about your SoC ==&lt;br /&gt;
&lt;br /&gt;
In order to begin mainlining your SoC, you need to have the following bits of information:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;codenames&#039;&#039;&#039; of the SoC. Qualcomm SoCs appear to have two codenames&amp;lt;ref&amp;gt;The names of these codenames have been sourced from [https://wiki.postmarketos.org/wiki/Qualcomm_Snapdragon_8_Gen_1/8%2B_Gen_1/7%2B_Gen_2_(SM8450/SM8475/SM7475) the postmarketOS wiki page for the Snapdragon 8 Gen 1, not sure where that is sourced from.&amp;lt;/ref&amp;gt;:&lt;br /&gt;
** &#039;&#039;Board codename&#039;&#039; (&amp;quot;DTS nickname&amp;quot;?) - you&#039;ll find it in the driver names on the device, as well as in the main compatible string of the devicetree. This is what&#039;s used across most of the downstream kernel.&lt;br /&gt;
** &#039;&#039;Platform codename&#039;&#039;. Presumably shared between multiple SoCs from the same family.&lt;br /&gt;
** Since SM7635 (&amp;quot;Volcano&amp;quot;/&amp;quot;Milos&amp;quot;), Qualcomm has changed their policy around driver/compatible naming in mainline and now expects developers to use the platform codename instead&amp;lt;ref&amp;gt;https://lore.kernel.org/lkml/888a7598-38d9-4640-9823-2b073da006f4@kernel.org/&amp;lt;/ref&amp;gt;. If you&#039;re unsure of the platform codename for your device, you can send the Qualcomm folks an email and ask them directly&amp;lt;ref&amp;gt;I ended up getting [https://lore.kernel.org/lkml/c379aad4-96f6-4134-8b90-0f1eec8001a3@oss.qualcomm.com/ a public reply to my query for SM7435].&amp;lt;/ref&amp;gt;, or just use the model name for now and let them correct you (as was done in the Milos case).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;downstream kernel&#039;&#039;&#039;; preferably the one for your device, but you can also use the kernel from another device with the same SoC, or - as a last resort - any kernel with the relevant SoC drivers (hint: search by downstream codename).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;&amp;lt;code&amp;gt;qcom_proprietary_devicetree&amp;lt;/code&amp;gt;&#039;&#039;&#039; or similar repo with the DTSI source files (because they&#039;re not in the kernel repo for whatever reason...). Search for &amp;lt;code&amp;gt;(downstream codename).dtsi&amp;lt;/code&amp;gt; on GitHub and you&#039;ll find the right repository eventually.&lt;br /&gt;
* An &#039;&#039;&#039;extracted DTB from your device&#039;&#039;&#039;. Dump this from a running device using FDT (todo: instructions, would probably be good on a generic page, maybe subpage of [[Devicetree]])?&lt;br /&gt;
* Find a similar SoC that is already supported. Usually flagship SoCs are available in mainline; try to find a flagship from around the same time as the SoC you&#039;re mainlining. Find its DTSIs as well; then you can compare the differences between downstream and mainline for the upstreamed SoC, and correlate them with differences in your SoC. You&#039;ll also be able to check the other SoC&#039;s drivers and use them as a base for your own drivers.&lt;br /&gt;
&lt;br /&gt;
== Adding the DTSI ==&lt;br /&gt;
&lt;br /&gt;
todo&lt;br /&gt;
&lt;br /&gt;
== Porting individual parts ==&lt;br /&gt;
&lt;br /&gt;
=== Clock controllers ===&lt;br /&gt;
&lt;br /&gt;
On recent Qualcomm SoCs, the downstream kernel uses the mainline Qualcomm clock driver with only &#039;&#039;some&#039;&#039; vendor-specific quirks. This means that the clock drivers and their relevant headers can pretty much be copied verbatim from downstream, with some slight modifications.&lt;br /&gt;
&lt;br /&gt;
First, create the &#039;&#039;&#039;GCC&#039;&#039;&#039; driver. Open &amp;lt;code&amp;gt;driver/clk/qcom/Kconfig&amp;lt;/code&amp;gt; and add the relevant Kconfig option for your SoC (remember to keep it ordered alphabetically):&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;kconfig&amp;quot;&amp;gt;&lt;br /&gt;
config SM_GCC_xxxx&lt;br /&gt;
	tristate &amp;quot;SMxxxx Global Clock Controller&amp;quot;&lt;br /&gt;
	depends on ARM64 || COMPILE_TEST&lt;br /&gt;
	select QCOM_GDSC&lt;br /&gt;
	help&lt;br /&gt;
	  Support for the global clock controller on SMxxxx devices.&lt;br /&gt;
	  Say Y if you want to use peripheral devices such as UART,&lt;br /&gt;
	  SPI, I2C, USB, SD/UFS, PCIe etc.&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/Makefile&amp;lt;/code&amp;gt; and add the relevant entry:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;makefile&amp;quot;&amp;gt;&lt;br /&gt;
obj-$(CONFIG_SM_GCC_xxxx) += gcc-smXXXX.o&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/gcc-smXXXX.c&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Paste the initialization code from another GCC driver (&amp;lt;syntaxhighlight inline lang=&amp;quot;c&amp;quot;&amp;gt;static struct platform_driver gcc_smXXXX_driver&amp;lt;/syntaxhighlight&amp;gt; and onwards.)&lt;br /&gt;
&lt;br /&gt;
== Porting the PMIC(s) ==&lt;br /&gt;
&lt;br /&gt;
Qualcomm devices use &#039;&#039;multiple&#039;&#039; PMICs for different purposes. Often, the PMIC is paired with an SoC or series of SoCs.&lt;br /&gt;
&lt;br /&gt;
== References ==&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=106</id>
		<title>User:Knuxify/Draft:Qualcomm/Adding a new SoC to mainline Linux</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=106"/>
		<updated>2026-02-02T19:06:38Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Subpage of|Qualcomm}}&lt;br /&gt;
{{Work-in-progress page|note=Currently in the middle of finding this out in real time :)}}&lt;br /&gt;
&lt;br /&gt;
This guide will cover the process of adding support for a recent (~2020 or newer, todo?) Qualcomm SoC into mainline Linux. Most of the information contained within is also applicable to older chips, though more manual effort may be needed to get these to run. &amp;lt;!--For the U-Boot guide, see TODO.--&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This guide was tested with the SM7435. Some details might be different for other SoCs. If you have any hints, please contribute!&lt;br /&gt;
&lt;br /&gt;
== High-level overview ==&lt;br /&gt;
&lt;br /&gt;
{{todo|Some of this will have to be moved out to the top-level Qualcomm page}}&lt;br /&gt;
&lt;br /&gt;
The basic components of a Qualcomm SoC are:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;GCC&#039;&#039;&#039;, or &#039;&#039;Global Clock Controller&#039;&#039;; as the name suggests, it is the primary clock controller for most components.&lt;br /&gt;
* The other clock controllers: &#039;&#039;&#039;CAMCC&#039;&#039;&#039;, &#039;&#039;&#039;DISPCC&#039;&#039;&#039;, &#039;&#039;&#039;GPUCC&#039;&#039;&#039; and &#039;&#039;&#039;VIDEOCC&#039;&#039;&#039;.&lt;br /&gt;
* The &#039;&#039;&#039;RPM&#039;&#039;&#039;, or &#039;&#039;Resource and Power Manager&#039;&#039; (&#039;&#039;&#039;RPMH&#039;&#039;&#039; or RPM &#039;&#039;Hardened&#039;&#039; in SDM845 and later); todo explanation from [https://wiki.postmarketos.org/wiki/Qualcomm_Glossary qcom glossary].&lt;br /&gt;
** Under the RPM is the &#039;&#039;&#039;RPM(H)CC&#039;&#039;&#039; (&#039;&#039;RPM clock controller&#039;&#039;) and &#039;&#039;&#039;RPM(H)PD&#039;&#039;&#039; (&#039;&#039;RPM power domains&#039;&#039;).&lt;br /&gt;
* &#039;&#039;&#039;QUP&#039;&#039;&#039;, or &#039;&#039;Qualcomm Universal Peripheral&#039;&#039;; the part of the SoC that provides I2C or SPI busses, as well as UART.&lt;br /&gt;
* &#039;&#039;&#039;TLMM&#039;&#039;&#039; (&#039;&#039;Top Level Mode Multiplexer&#039;&#039;); provides pinmux and GPIO pins.&lt;br /&gt;
* Many &#039;&#039;&#039;NOC&#039;&#039;&#039; interconnects (&#039;&#039;Network on Chip&#039;&#039;).&lt;br /&gt;
* A timer and an interrupt controller, both standard ARM parts.&lt;br /&gt;
&lt;br /&gt;
These are just the most low-level components; from there, we can move on to the higher-level ones:&lt;br /&gt;
&lt;br /&gt;
* Thermal monitoring sensor&lt;br /&gt;
* USB host controller and PHY&lt;br /&gt;
* Display controller and DSI PHY&lt;br /&gt;
* GPU&lt;br /&gt;
* etc.&lt;br /&gt;
&lt;br /&gt;
This page will touch on mainline porting of most of these parts.&lt;br /&gt;
&lt;br /&gt;
== Finding information about your SoC ==&lt;br /&gt;
&lt;br /&gt;
In order to begin mainlining your SoC, you need to have the following bits of information:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;codenames&#039;&#039;&#039; of the SoC. Qualcomm SoCs appear to have two codenames:&lt;br /&gt;
** &#039;&#039;&amp;quot;DTS nickname&amp;quot;&#039;&#039; (board name?). You&#039;ll find it in the driver names on the device, as well as in the main compatible string of the devicetree. This is what&#039;s used across most of the downstream kernel.&lt;br /&gt;
** &#039;&#039;Platform codename(?)&#039;&#039;. Presumably shared between multiple SoCs from the same family.&lt;br /&gt;
** Since SM7635 (&amp;quot;Volcano&amp;quot;/&amp;quot;Milos&amp;quot;), Qualcomm has changed their policy around driver/compatible naming in mainline and now expects developers to use the platform codename instead&amp;lt;ref&amp;gt;https://lore.kernel.org/lkml/888a7598-38d9-4640-9823-2b073da006f4@kernel.org/&amp;lt;/ref&amp;gt;. If you&#039;re unsure of the platform codename for your device, you can send the Qualcomm folks an email and ask them directly&amp;lt;ref&amp;gt;I ended up getting [https://lore.kernel.org/lkml/c379aad4-96f6-4134-8b90-0f1eec8001a3@oss.qualcomm.com/ a public reply to my query for SM7435].&amp;lt;/ref&amp;gt;, or just use the model name for now and let them correct you (as was done in the Milos case).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;downstream kernel&#039;&#039;&#039;; preferably the one for your device, but you can also use the kernel from another device with the same SoC, or - as a last resort - any kernel with the relevant SoC drivers (hint: search by downstream codename).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;&amp;lt;code&amp;gt;qcom_proprietary_devicetree&amp;lt;/code&amp;gt;&#039;&#039;&#039; or similar repo with the DTSI source files (because they&#039;re not in the kernel repo for whatever reason...). Search for &amp;lt;code&amp;gt;(downstream codename).dtsi&amp;lt;/code&amp;gt; on GitHub and you&#039;ll find the right repository eventually.&lt;br /&gt;
* An &#039;&#039;&#039;extracted DTB from your device&#039;&#039;&#039;. Dump this from a running device using FDT (todo: instructions, would probably be good on a generic page, maybe subpage of [[Devicetree]])?&lt;br /&gt;
* Find a similar SoC that is already supported. Usually flagship SoCs are available in mainline; try to find a flagship from around the same time as the SoC you&#039;re mainlining. Find its DTSIs as well; then you can compare the differences between downstream and mainline for the upstreamed SoC, and correlate them with differences in your SoC. You&#039;ll also be able to check the other SoC&#039;s drivers and use them as a base for your own drivers.&lt;br /&gt;
&lt;br /&gt;
== Adding the DTSI ==&lt;br /&gt;
&lt;br /&gt;
todo&lt;br /&gt;
&lt;br /&gt;
== Porting individual parts ==&lt;br /&gt;
&lt;br /&gt;
=== Clock controllers ===&lt;br /&gt;
&lt;br /&gt;
On recent Qualcomm SoCs, the downstream kernel uses the mainline Qualcomm clock driver with only &#039;&#039;some&#039;&#039; vendor-specific quirks. This means that the clock drivers and their relevant headers can pretty much be copied verbatim from downstream, with some slight modifications.&lt;br /&gt;
&lt;br /&gt;
First, create the &#039;&#039;&#039;GCC&#039;&#039;&#039; driver. Open &amp;lt;code&amp;gt;driver/clk/qcom/Kconfig&amp;lt;/code&amp;gt; and add the relevant Kconfig option for your SoC (remember to keep it ordered alphabetically):&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;kconfig&amp;quot;&amp;gt;&lt;br /&gt;
config SM_GCC_xxxx&lt;br /&gt;
	tristate &amp;quot;SMxxxx Global Clock Controller&amp;quot;&lt;br /&gt;
	depends on ARM64 || COMPILE_TEST&lt;br /&gt;
	select QCOM_GDSC&lt;br /&gt;
	help&lt;br /&gt;
	  Support for the global clock controller on SMxxxx devices.&lt;br /&gt;
	  Say Y if you want to use peripheral devices such as UART,&lt;br /&gt;
	  SPI, I2C, USB, SD/UFS, PCIe etc.&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/Makefile&amp;lt;/code&amp;gt; and add the relevant entry:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;makefile&amp;quot;&amp;gt;&lt;br /&gt;
obj-$(CONFIG_SM_GCC_xxxx) += gcc-smXXXX.o&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/gcc-smXXXX.c&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Paste the initialization code from another GCC driver (&amp;lt;syntaxhighlight inline lang=&amp;quot;c&amp;quot;&amp;gt;static struct platform_driver gcc_smXXXX_driver&amp;lt;/syntaxhighlight&amp;gt; and onwards.)&lt;br /&gt;
&lt;br /&gt;
== Porting the PMIC(s) ==&lt;br /&gt;
&lt;br /&gt;
Qualcomm devices use &#039;&#039;multiple&#039;&#039; PMICs for different purposes. Often, the PMIC is paired with an SoC or series of SoCs.&lt;br /&gt;
&lt;br /&gt;
== References ==&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=105</id>
		<title>User:Knuxify/Draft:Qualcomm/Adding a new SoC to mainline Linux</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=105"/>
		<updated>2026-02-02T19:05:49Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: /* Finding information about your SoC */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Subpage of|Qualcomm}}&lt;br /&gt;
{{Work-in-progress page|note=Currently in the middle of finding this out in real time :)}}&lt;br /&gt;
&lt;br /&gt;
This guide will cover the process of adding support for a recent (~2020 or newer, todo?) Qualcomm SoC into mainline Linux. Most of the information contained within is also applicable to older chips, though more manual effort may be needed to get these to run. &amp;lt;!--For the U-Boot guide, see TODO.--&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This guide was tested with the SM7435. Some details might be different for other SoCs. If you have any hints, please contribute!&lt;br /&gt;
&lt;br /&gt;
== High-level overview ==&lt;br /&gt;
&lt;br /&gt;
{{todo|Some of this will have to be moved out to the top-level Qualcomm page}}&lt;br /&gt;
&lt;br /&gt;
The basic components of a Qualcomm SoC are:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;GCC&#039;&#039;&#039;, or &#039;&#039;Global Clock Controller&#039;&#039;; as the name suggests, it is the primary clock controller for most components.&lt;br /&gt;
* The other clock controllers: &#039;&#039;&#039;CAMCC&#039;&#039;&#039;, &#039;&#039;&#039;DISPCC&#039;&#039;&#039;, &#039;&#039;&#039;GPUCC&#039;&#039;&#039; and &#039;&#039;&#039;VIDEOCC&#039;&#039;&#039;.&lt;br /&gt;
* The &#039;&#039;&#039;RPM&#039;&#039;&#039;, or &#039;&#039;Resource and Power Manager&#039;&#039; (&#039;&#039;&#039;RPMH&#039;&#039;&#039; or RPM &#039;&#039;Hardened&#039;&#039; in SDM845 and later); todo explanation from [https://wiki.postmarketos.org/wiki/Qualcomm_Glossary qcom glossary].&lt;br /&gt;
** Under the RPM is the &#039;&#039;&#039;RPM(H)CC&#039;&#039;&#039; (&#039;&#039;RPM clock controller&#039;&#039;) and &#039;&#039;&#039;RPM(H)PD&#039;&#039;&#039; (&#039;&#039;RPM power domains&#039;&#039;).&lt;br /&gt;
* &#039;&#039;&#039;QUP&#039;&#039;&#039;, or &#039;&#039;Qualcomm Universal Peripheral&#039;&#039;; the part of the SoC that provides I2C or SPI busses, as well as UART.&lt;br /&gt;
* &#039;&#039;&#039;TLMM&#039;&#039;&#039; (&#039;&#039;Top Level Mode Multiplexer&#039;&#039;); provides pinmux and GPIO pins.&lt;br /&gt;
* Many &#039;&#039;&#039;NOC&#039;&#039;&#039; interconnects (&#039;&#039;Network on Chip&#039;&#039;).&lt;br /&gt;
* A timer and an interrupt controller, both standard ARM parts.&lt;br /&gt;
&lt;br /&gt;
These are just the most low-level components; from there, we can move on to the higher-level ones:&lt;br /&gt;
&lt;br /&gt;
* Thermal monitoring sensor&lt;br /&gt;
* USB host controller and PHY&lt;br /&gt;
* Display controller and DSI PHY&lt;br /&gt;
* GPU&lt;br /&gt;
* etc.&lt;br /&gt;
&lt;br /&gt;
This page will touch on mainline porting of most of these parts.&lt;br /&gt;
&lt;br /&gt;
== Finding information about your SoC ==&lt;br /&gt;
&lt;br /&gt;
In order to begin mainlining your SoC, you need to have the following bits of information:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;codenames&#039;&#039;&#039; of the SoC. Qualcomm SoCs appear to have two codenames:&lt;br /&gt;
** &#039;&#039;&amp;quot;DTS nickname&amp;quot;&#039;&#039; (board name?). You&#039;ll find it in the driver names on the device, as well as in the main compatible string of the devicetree. This is what&#039;s used across most of the downstream kernel.&lt;br /&gt;
** &#039;&#039;Platform codename(?)&#039;&#039;. Presumably shared between multiple SoCs from the same family.&lt;br /&gt;
** Since SM7635 (&amp;quot;Volcano&amp;quot;/&amp;quot;Milos&amp;quot;), Qualcomm has changed their policy around driver/compatible naming in mainline and now expects developers to use the platform codename instead&amp;lt;ref&amp;gt;https://lore.kernel.org/lkml/c379aad4-96f6-4134-8b90-0f1eec8001a3@oss.qualcomm.com/&amp;lt;/ref&amp;gt;. If you&#039;re unsure of the platform codename for your device, you can send the Qualcomm folks an email and ask them directly&amp;lt;ref&amp;gt;I ended up getting [https://lore.kernel.org/lkml/c379aad4-96f6-4134-8b90-0f1eec8001a3@oss.qualcomm.com/ a public reply to my query for SM7435].&amp;lt;/ref&amp;gt;, or just use the model name for now and let them correct you (as was done in the Milos case).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;downstream kernel&#039;&#039;&#039;; preferably the one for your device, but you can also use the kernel from another device with the same SoC, or - as a last resort - any kernel with the relevant SoC drivers (hint: search by downstream codename).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;&amp;lt;code&amp;gt;qcom_proprietary_devicetree&amp;lt;/code&amp;gt;&#039;&#039;&#039; or similar repo with the DTSI source files (because they&#039;re not in the kernel repo for whatever reason...). Search for &amp;lt;code&amp;gt;(downstream codename).dtsi&amp;lt;/code&amp;gt; on GitHub and you&#039;ll find the right repository eventually.&lt;br /&gt;
* An &#039;&#039;&#039;extracted DTB from your device&#039;&#039;&#039;. Dump this from a running device using FDT (todo: instructions, would probably be good on a generic page, maybe subpage of [[Devicetree]])?&lt;br /&gt;
* Find a similar SoC that is already supported. Usually flagship SoCs are available in mainline; try to find a flagship from around the same time as the SoC you&#039;re mainlining. Find its DTSIs as well; then you can compare the differences between downstream and mainline for the upstreamed SoC, and correlate them with differences in your SoC. You&#039;ll also be able to check the other SoC&#039;s drivers and use them as a base for your own drivers.&lt;br /&gt;
&lt;br /&gt;
== Adding the DTSI ==&lt;br /&gt;
&lt;br /&gt;
todo&lt;br /&gt;
&lt;br /&gt;
== Porting individual parts ==&lt;br /&gt;
&lt;br /&gt;
=== Clock controllers ===&lt;br /&gt;
&lt;br /&gt;
On recent Qualcomm SoCs, the downstream kernel uses the mainline Qualcomm clock driver with only &#039;&#039;some&#039;&#039; vendor-specific quirks. This means that the clock drivers and their relevant headers can pretty much be copied verbatim from downstream, with some slight modifications.&lt;br /&gt;
&lt;br /&gt;
First, create the &#039;&#039;&#039;GCC&#039;&#039;&#039; driver. Open &amp;lt;code&amp;gt;driver/clk/qcom/Kconfig&amp;lt;/code&amp;gt; and add the relevant Kconfig option for your SoC (remember to keep it ordered alphabetically):&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;kconfig&amp;quot;&amp;gt;&lt;br /&gt;
config SM_GCC_xxxx&lt;br /&gt;
	tristate &amp;quot;SMxxxx Global Clock Controller&amp;quot;&lt;br /&gt;
	depends on ARM64 || COMPILE_TEST&lt;br /&gt;
	select QCOM_GDSC&lt;br /&gt;
	help&lt;br /&gt;
	  Support for the global clock controller on SMxxxx devices.&lt;br /&gt;
	  Say Y if you want to use peripheral devices such as UART,&lt;br /&gt;
	  SPI, I2C, USB, SD/UFS, PCIe etc.&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/Makefile&amp;lt;/code&amp;gt; and add the relevant entry:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;makefile&amp;quot;&amp;gt;&lt;br /&gt;
obj-$(CONFIG_SM_GCC_xxxx) += gcc-smXXXX.o&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/gcc-smXXXX.c&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Paste the initialization code from another GCC driver (&amp;lt;syntaxhighlight inline lang=&amp;quot;c&amp;quot;&amp;gt;static struct platform_driver gcc_smXXXX_driver&amp;lt;/syntaxhighlight&amp;gt; and onwards.)&lt;br /&gt;
&lt;br /&gt;
== Porting the PMIC(s) ==&lt;br /&gt;
&lt;br /&gt;
Qualcomm devices use &#039;&#039;multiple&#039;&#039; PMICs for different purposes. Often, the PMIC is paired with an SoC or series of SoCs.&lt;br /&gt;
&lt;br /&gt;
== References ==&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=104</id>
		<title>User:Knuxify/Draft:Qualcomm/Adding a new SoC to mainline Linux</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=104"/>
		<updated>2026-02-02T18:57:37Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: /* Finding information about your SoC */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Subpage of|Qualcomm}}&lt;br /&gt;
{{Work-in-progress page|note=Currently in the middle of finding this out in real time :)}}&lt;br /&gt;
&lt;br /&gt;
This guide will cover the process of adding support for a recent (~2020 or newer, todo?) Qualcomm SoC into mainline Linux. Most of the information contained within is also applicable to older chips, though more manual effort may be needed to get these to run. &amp;lt;!--For the U-Boot guide, see TODO.--&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This guide was tested with the SM7435. Some details might be different for other SoCs. If you have any hints, please contribute!&lt;br /&gt;
&lt;br /&gt;
== High-level overview ==&lt;br /&gt;
&lt;br /&gt;
{{todo|Some of this will have to be moved out to the top-level Qualcomm page}}&lt;br /&gt;
&lt;br /&gt;
The basic components of a Qualcomm SoC are:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;GCC&#039;&#039;&#039;, or &#039;&#039;Global Clock Controller&#039;&#039;; as the name suggests, it is the primary clock controller for most components.&lt;br /&gt;
* The other clock controllers: &#039;&#039;&#039;CAMCC&#039;&#039;&#039;, &#039;&#039;&#039;DISPCC&#039;&#039;&#039;, &#039;&#039;&#039;GPUCC&#039;&#039;&#039; and &#039;&#039;&#039;VIDEOCC&#039;&#039;&#039;.&lt;br /&gt;
* The &#039;&#039;&#039;RPM&#039;&#039;&#039;, or &#039;&#039;Resource and Power Manager&#039;&#039; (&#039;&#039;&#039;RPMH&#039;&#039;&#039; or RPM &#039;&#039;Hardened&#039;&#039; in SDM845 and later); todo explanation from [https://wiki.postmarketos.org/wiki/Qualcomm_Glossary qcom glossary].&lt;br /&gt;
** Under the RPM is the &#039;&#039;&#039;RPM(H)CC&#039;&#039;&#039; (&#039;&#039;RPM clock controller&#039;&#039;) and &#039;&#039;&#039;RPM(H)PD&#039;&#039;&#039; (&#039;&#039;RPM power domains&#039;&#039;).&lt;br /&gt;
* &#039;&#039;&#039;QUP&#039;&#039;&#039;, or &#039;&#039;Qualcomm Universal Peripheral&#039;&#039;; the part of the SoC that provides I2C or SPI busses, as well as UART.&lt;br /&gt;
* &#039;&#039;&#039;TLMM&#039;&#039;&#039; (&#039;&#039;Top Level Mode Multiplexer&#039;&#039;); provides pinmux and GPIO pins.&lt;br /&gt;
* Many &#039;&#039;&#039;NOC&#039;&#039;&#039; interconnects (&#039;&#039;Network on Chip&#039;&#039;).&lt;br /&gt;
* A timer and an interrupt controller, both standard ARM parts.&lt;br /&gt;
&lt;br /&gt;
These are just the most low-level components; from there, we can move on to the higher-level ones:&lt;br /&gt;
&lt;br /&gt;
* Thermal monitoring sensor&lt;br /&gt;
* USB host controller and PHY&lt;br /&gt;
* Display controller and DSI PHY&lt;br /&gt;
* GPU&lt;br /&gt;
* etc.&lt;br /&gt;
&lt;br /&gt;
This page will touch on mainline porting of most of these parts.&lt;br /&gt;
&lt;br /&gt;
== Finding information about your SoC ==&lt;br /&gt;
&lt;br /&gt;
In order to begin mainlining your SoC, you need to have the following bits of information:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;downstream codename&#039;&#039;&#039; (&amp;quot;DTS nickname&amp;quot;?) of your SoC. If you&#039;re lucky, it&#039;s probably already somewhere out there online. You&#039;ll find it in the driver names on the device, as well as in the main compatible string of the devicetree. This will be useful when looking things up in the downstream kernel, as it primarily uses the codename.&lt;br /&gt;
* The &#039;&#039;&#039;internal codename&#039;&#039;&#039; of your SoC. Around mid-2025, Qualcomm&#039;s mainline Linux engineers decided that instead of using the model name for SoC drivers, they should use the codename instead... except the codename in the downstream code isn&#039;t always the same as the &#039;&#039;actual&#039;&#039; SoC codename.&lt;br /&gt;
** Sometimes the downstream codename matches with the internal name (as might be the case for &amp;quot;waipio&amp;quot; given it&#039;s mentioned alongside the others in [https://mysupport.qualcomm.com/supportforums/s/question/0D54V00007gUfXASA0/whats-the-difference-of-v69-and-v73 this random Qualcomm support forums post]), other times it&#039;s different (SM7435 uses &amp;quot;parrot&amp;quot; in the kernel but is actually called &amp;quot;netrani&amp;quot;&amp;lt;ref&amp;gt;https://lore.kernel.org/lkml/c379aad4-96f6-4134-8b90-0f1eec8001a3@oss.qualcomm.com/&amp;lt;/ref&amp;gt;, SM7635 uses &amp;quot;volcano&amp;quot; in downstream but is actually called &amp;quot;milos&amp;quot;).&lt;br /&gt;
** &#039;&#039;Mere mortals&#039;&#039; shall not know these codenames... but you can probably ask your friendly neighborhood sympathizer of the mainline cause&amp;lt;ref&amp;gt;https://lore.kernel.org/lkml/888a7598-38d9-4640-9823-2b073da006f4@kernel.org/&amp;lt;/ref&amp;gt;.&lt;br /&gt;
* A copy of the &#039;&#039;&#039;downstream kernel&#039;&#039;&#039;; preferably the one for your device, but you can also use the kernel from another device with the same SoC, or - as a last resort - any kernel with the relevant SoC drivers (hint: search by downstream codename).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;&amp;lt;code&amp;gt;qcom_proprietary_devicetree&amp;lt;/code&amp;gt;&#039;&#039;&#039; or similar repo with the DTSI source files (because they&#039;re not in the kernel repo for whatever reason...). Search for &amp;lt;code&amp;gt;(downstream codename).dtsi&amp;lt;/code&amp;gt; on GitHub and you&#039;ll find the right repository eventually.&lt;br /&gt;
* An &#039;&#039;&#039;extracted DTB from your device&#039;&#039;&#039;. Dump this from a running device using FDT (todo: instructions, would probably be good on a generic page, maybe subpage of [[Devicetree]])?&lt;br /&gt;
* Find a similar SoC that is already supported. Usually flagship SoCs are available in mainline; try to find a flagship from around the same time as the SoC you&#039;re mainlining. Find its DTSIs as well; then you can compare the differences between downstream and mainline for the upstreamed SoC, and correlate them with differences in your SoC. You&#039;ll also be able to check the other SoC&#039;s drivers and use them as a base for your own drivers.&lt;br /&gt;
&lt;br /&gt;
== Adding the DTSI ==&lt;br /&gt;
&lt;br /&gt;
todo&lt;br /&gt;
&lt;br /&gt;
== Porting individual parts ==&lt;br /&gt;
&lt;br /&gt;
=== Clock controllers ===&lt;br /&gt;
&lt;br /&gt;
On recent Qualcomm SoCs, the downstream kernel uses the mainline Qualcomm clock driver with only &#039;&#039;some&#039;&#039; vendor-specific quirks. This means that the clock drivers and their relevant headers can pretty much be copied verbatim from downstream, with some slight modifications.&lt;br /&gt;
&lt;br /&gt;
First, create the &#039;&#039;&#039;GCC&#039;&#039;&#039; driver. Open &amp;lt;code&amp;gt;driver/clk/qcom/Kconfig&amp;lt;/code&amp;gt; and add the relevant Kconfig option for your SoC (remember to keep it ordered alphabetically):&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;kconfig&amp;quot;&amp;gt;&lt;br /&gt;
config SM_GCC_xxxx&lt;br /&gt;
	tristate &amp;quot;SMxxxx Global Clock Controller&amp;quot;&lt;br /&gt;
	depends on ARM64 || COMPILE_TEST&lt;br /&gt;
	select QCOM_GDSC&lt;br /&gt;
	help&lt;br /&gt;
	  Support for the global clock controller on SMxxxx devices.&lt;br /&gt;
	  Say Y if you want to use peripheral devices such as UART,&lt;br /&gt;
	  SPI, I2C, USB, SD/UFS, PCIe etc.&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/Makefile&amp;lt;/code&amp;gt; and add the relevant entry:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;makefile&amp;quot;&amp;gt;&lt;br /&gt;
obj-$(CONFIG_SM_GCC_xxxx) += gcc-smXXXX.o&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/gcc-smXXXX.c&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Paste the initialization code from another GCC driver (&amp;lt;syntaxhighlight inline lang=&amp;quot;c&amp;quot;&amp;gt;static struct platform_driver gcc_smXXXX_driver&amp;lt;/syntaxhighlight&amp;gt; and onwards.)&lt;br /&gt;
&lt;br /&gt;
== Porting the PMIC(s) ==&lt;br /&gt;
&lt;br /&gt;
Qualcomm devices use &#039;&#039;multiple&#039;&#039; PMICs for different purposes. Often, the PMIC is paired with an SoC or series of SoCs.&lt;br /&gt;
&lt;br /&gt;
== References ==&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=103</id>
		<title>User:Knuxify/Draft:Qualcomm/Adding a new SoC to mainline Linux</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=103"/>
		<updated>2026-02-02T18:48:35Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: /* Finding information about your SoC */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Subpage of|Qualcomm}}&lt;br /&gt;
{{Work-in-progress page|note=Currently in the middle of finding this out in real time :)}}&lt;br /&gt;
&lt;br /&gt;
This guide will cover the process of adding support for a recent (~2020 or newer, todo?) Qualcomm SoC into mainline Linux. Most of the information contained within is also applicable to older chips, though more manual effort may be needed to get these to run. &amp;lt;!--For the U-Boot guide, see TODO.--&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This guide was tested with the SM7435. Some details might be different for other SoCs. If you have any hints, please contribute!&lt;br /&gt;
&lt;br /&gt;
== High-level overview ==&lt;br /&gt;
&lt;br /&gt;
{{todo|Some of this will have to be moved out to the top-level Qualcomm page}}&lt;br /&gt;
&lt;br /&gt;
The basic components of a Qualcomm SoC are:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;GCC&#039;&#039;&#039;, or &#039;&#039;Global Clock Controller&#039;&#039;; as the name suggests, it is the primary clock controller for most components.&lt;br /&gt;
* The other clock controllers: &#039;&#039;&#039;CAMCC&#039;&#039;&#039;, &#039;&#039;&#039;DISPCC&#039;&#039;&#039;, &#039;&#039;&#039;GPUCC&#039;&#039;&#039; and &#039;&#039;&#039;VIDEOCC&#039;&#039;&#039;.&lt;br /&gt;
* The &#039;&#039;&#039;RPM&#039;&#039;&#039;, or &#039;&#039;Resource and Power Manager&#039;&#039; (&#039;&#039;&#039;RPMH&#039;&#039;&#039; or RPM &#039;&#039;Hardened&#039;&#039; in SDM845 and later); todo explanation from [https://wiki.postmarketos.org/wiki/Qualcomm_Glossary qcom glossary].&lt;br /&gt;
** Under the RPM is the &#039;&#039;&#039;RPM(H)CC&#039;&#039;&#039; (&#039;&#039;RPM clock controller&#039;&#039;) and &#039;&#039;&#039;RPM(H)PD&#039;&#039;&#039; (&#039;&#039;RPM power domains&#039;&#039;).&lt;br /&gt;
* &#039;&#039;&#039;QUP&#039;&#039;&#039;, or &#039;&#039;Qualcomm Universal Peripheral&#039;&#039;; the part of the SoC that provides I2C or SPI busses, as well as UART.&lt;br /&gt;
* &#039;&#039;&#039;TLMM&#039;&#039;&#039; (&#039;&#039;Top Level Mode Multiplexer&#039;&#039;); provides pinmux and GPIO pins.&lt;br /&gt;
* Many &#039;&#039;&#039;NOC&#039;&#039;&#039; interconnects (&#039;&#039;Network on Chip&#039;&#039;).&lt;br /&gt;
* A timer and an interrupt controller, both standard ARM parts.&lt;br /&gt;
&lt;br /&gt;
These are just the most low-level components; from there, we can move on to the higher-level ones:&lt;br /&gt;
&lt;br /&gt;
* Thermal monitoring sensor&lt;br /&gt;
* USB host controller and PHY&lt;br /&gt;
* Display controller and DSI PHY&lt;br /&gt;
* GPU&lt;br /&gt;
* etc.&lt;br /&gt;
&lt;br /&gt;
This page will touch on mainline porting of most of these parts.&lt;br /&gt;
&lt;br /&gt;
== Finding information about your SoC ==&lt;br /&gt;
&lt;br /&gt;
In order to begin mainlining your SoC, you need to have the following bits of information:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;downstream codename&#039;&#039;&#039; (&amp;quot;DTS nickname&amp;quot;?) of your SoC. If you&#039;re lucky, it&#039;s probably already somewhere out there online. You&#039;ll find it in the driver names on the device. This will be useful when looking things up in the downstream kernel, as it primarily uses the codename, whereas mainline uses the model number.&lt;br /&gt;
* The &#039;&#039;&#039;internal codename&#039;&#039;&#039; of your SoC. Around mid-2025, Qualcomm&#039;s mainline Linux engineers decided that instead of using the model name for SoC drivers, they should use the codename instead... except the codename in downstream isn&#039;t always the same as the &#039;&#039;actual&#039;&#039; codename.&lt;br /&gt;
** &#039;&#039;Mere mortals&#039;&#039; shall not know these codenames... but you can probably ask your friendly neighborhood sympathizer of the mainline cause&amp;lt;ref&amp;gt;https://lore.kernel.org/lkml/888a7598-38d9-4640-9823-2b073da006f4@kernel.org/&amp;lt;/ref&amp;gt;.&lt;br /&gt;
** Sometimes the downstream codename matches with the internal name (as might be the case for &amp;quot;waipio&amp;quot; given it&#039;s mentioned alongside the others in [https://mysupport.qualcomm.com/supportforums/s/question/0D54V00007gUfXASA0/whats-the-difference-of-v69-and-v73 this random Qualcomm support forums post]), othertimes it&#039;s different (SM7435 uses &amp;quot;parrot&amp;quot; in the kernel but is actually called &amp;quot;netrani&amp;quot;&amp;lt;ref&amp;gt;https://lore.kernel.org/lkml/c379aad4-96f6-4134-8b90-0f1eec8001a3@oss.qualcomm.com/&amp;lt;/ref&amp;gt;).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;downstream kernel&#039;&#039;&#039;; preferably the one for your device, but you can also use the kernel from another device with the same SoC, or - as a last resort - any kernel with the relevant SoC drivers (hint: search by downstream codename).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;&amp;lt;code&amp;gt;qcom_proprietary_devicetree&amp;lt;/code&amp;gt;&#039;&#039;&#039; or similar repo with the DTSI source files (because they&#039;re not in the kernel repo for whatever reason...). Search for &amp;lt;code&amp;gt;(downstream codename).dtsi&amp;lt;/code&amp;gt; on GitHub and you&#039;ll find the right repository eventually.&lt;br /&gt;
* An &#039;&#039;&#039;extracted DTB from your device&#039;&#039;&#039;. Dump this from a running device using FDT (todo: instructions, would probably be good on a generic page, maybe subpage of [[Devicetree]])?&lt;br /&gt;
* Find a similar SoC that is already supported. Usually flagship SoCs are available in mainline; try to find a flagship from around the same time as the SoC you&#039;re mainlining. Find its DTSIs as well; then you can compare the differences between downstream and mainline for the upstreamed SoC, and correlate them with differences in your SoC. You&#039;ll also be able to check the other SoC&#039;s drivers and use them as a base for your own drivers.&lt;br /&gt;
&lt;br /&gt;
== Adding the DTSI ==&lt;br /&gt;
&lt;br /&gt;
todo&lt;br /&gt;
&lt;br /&gt;
== Porting individual parts ==&lt;br /&gt;
&lt;br /&gt;
=== Clock controllers ===&lt;br /&gt;
&lt;br /&gt;
On recent Qualcomm SoCs, the downstream kernel uses the mainline Qualcomm clock driver with only &#039;&#039;some&#039;&#039; vendor-specific quirks. This means that the clock drivers and their relevant headers can pretty much be copied verbatim from downstream, with some slight modifications.&lt;br /&gt;
&lt;br /&gt;
First, create the &#039;&#039;&#039;GCC&#039;&#039;&#039; driver. Open &amp;lt;code&amp;gt;driver/clk/qcom/Kconfig&amp;lt;/code&amp;gt; and add the relevant Kconfig option for your SoC (remember to keep it ordered alphabetically):&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;kconfig&amp;quot;&amp;gt;&lt;br /&gt;
config SM_GCC_xxxx&lt;br /&gt;
	tristate &amp;quot;SMxxxx Global Clock Controller&amp;quot;&lt;br /&gt;
	depends on ARM64 || COMPILE_TEST&lt;br /&gt;
	select QCOM_GDSC&lt;br /&gt;
	help&lt;br /&gt;
	  Support for the global clock controller on SMxxxx devices.&lt;br /&gt;
	  Say Y if you want to use peripheral devices such as UART,&lt;br /&gt;
	  SPI, I2C, USB, SD/UFS, PCIe etc.&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/Makefile&amp;lt;/code&amp;gt; and add the relevant entry:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;makefile&amp;quot;&amp;gt;&lt;br /&gt;
obj-$(CONFIG_SM_GCC_xxxx) += gcc-smXXXX.o&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/gcc-smXXXX.c&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Paste the initialization code from another GCC driver (&amp;lt;syntaxhighlight inline lang=&amp;quot;c&amp;quot;&amp;gt;static struct platform_driver gcc_smXXXX_driver&amp;lt;/syntaxhighlight&amp;gt; and onwards.)&lt;br /&gt;
&lt;br /&gt;
== Porting the PMIC(s) ==&lt;br /&gt;
&lt;br /&gt;
Qualcomm devices use &#039;&#039;multiple&#039;&#039; PMICs for different purposes. Often, the PMIC is paired with an SoC or series of SoCs.&lt;br /&gt;
&lt;br /&gt;
== References ==&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=102</id>
		<title>User:Knuxify/Draft:Qualcomm/Adding a new SoC to mainline Linux</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=102"/>
		<updated>2026-02-02T18:38:30Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: /* Finding information about your SoC */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Subpage of|Qualcomm}}&lt;br /&gt;
{{Work-in-progress page|note=Currently in the middle of finding this out in real time :)}}&lt;br /&gt;
&lt;br /&gt;
This guide will cover the process of adding support for a recent (~2020 or newer, todo?) Qualcomm SoC into mainline Linux. Most of the information contained within is also applicable to older chips, though more manual effort may be needed to get these to run. &amp;lt;!--For the U-Boot guide, see TODO.--&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This guide was tested with the SM7435. Some details might be different for other SoCs. If you have any hints, please contribute!&lt;br /&gt;
&lt;br /&gt;
== High-level overview ==&lt;br /&gt;
&lt;br /&gt;
{{todo|Some of this will have to be moved out to the top-level Qualcomm page}}&lt;br /&gt;
&lt;br /&gt;
The basic components of a Qualcomm SoC are:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;GCC&#039;&#039;&#039;, or &#039;&#039;Global Clock Controller&#039;&#039;; as the name suggests, it is the primary clock controller for most components.&lt;br /&gt;
* The other clock controllers: &#039;&#039;&#039;CAMCC&#039;&#039;&#039;, &#039;&#039;&#039;DISPCC&#039;&#039;&#039;, &#039;&#039;&#039;GPUCC&#039;&#039;&#039; and &#039;&#039;&#039;VIDEOCC&#039;&#039;&#039;.&lt;br /&gt;
* The &#039;&#039;&#039;RPM&#039;&#039;&#039;, or &#039;&#039;Resource and Power Manager&#039;&#039; (&#039;&#039;&#039;RPMH&#039;&#039;&#039; or RPM &#039;&#039;Hardened&#039;&#039; in SDM845 and later); todo explanation from [https://wiki.postmarketos.org/wiki/Qualcomm_Glossary qcom glossary].&lt;br /&gt;
** Under the RPM is the &#039;&#039;&#039;RPM(H)CC&#039;&#039;&#039; (&#039;&#039;RPM clock controller&#039;&#039;) and &#039;&#039;&#039;RPM(H)PD&#039;&#039;&#039; (&#039;&#039;RPM power domains&#039;&#039;).&lt;br /&gt;
* &#039;&#039;&#039;QUP&#039;&#039;&#039;, or &#039;&#039;Qualcomm Universal Peripheral&#039;&#039;; the part of the SoC that provides I2C or SPI busses, as well as UART.&lt;br /&gt;
* &#039;&#039;&#039;TLMM&#039;&#039;&#039; (&#039;&#039;Top Level Mode Multiplexer&#039;&#039;); provides pinmux and GPIO pins.&lt;br /&gt;
* Many &#039;&#039;&#039;NOC&#039;&#039;&#039; interconnects (&#039;&#039;Network on Chip&#039;&#039;).&lt;br /&gt;
* A timer and an interrupt controller, both standard ARM parts.&lt;br /&gt;
&lt;br /&gt;
These are just the most low-level components; from there, we can move on to the higher-level ones:&lt;br /&gt;
&lt;br /&gt;
* Thermal monitoring sensor&lt;br /&gt;
* USB host controller and PHY&lt;br /&gt;
* Display controller and DSI PHY&lt;br /&gt;
* GPU&lt;br /&gt;
* etc.&lt;br /&gt;
&lt;br /&gt;
This page will touch on mainline porting of most of these parts.&lt;br /&gt;
&lt;br /&gt;
== Finding information about your SoC ==&lt;br /&gt;
&lt;br /&gt;
In order to begin mainlining your SoC, you need to have the following bits of information:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;downstream codename&#039;&#039;&#039; (&amp;quot;DTS nickname&amp;quot;?) of your SoC. If you&#039;re lucky, it&#039;s probably already somewhere out there online. You&#039;ll find it in the driver names on the device. This will be useful when looking things up in the downstream kernel, as it primarily uses the codename, whereas mainline uses the model number.&lt;br /&gt;
* The &#039;&#039;&#039;internal codename&#039;&#039;&#039; of your SoC. Around mid-2025, Qualcomm&#039;s mainline Linux engineers decided that instead of using the model name for SoC drivers, they should use the codename instead... except the codename they &#039;&#039;want&#039;&#039; you to use is different from the one that&#039;s plastered all over the downstream kernel.&lt;br /&gt;
** &#039;&#039;Mere mortals&#039;&#039; shall not know these codenames... but you can probably ask your friendly neighborhood sympathizer of the mainline cause&amp;lt;ref&amp;gt;https://lore.kernel.org/lkml/888a7598-38d9-4640-9823-2b073da006f4@kernel.org/&amp;lt;/ref&amp;gt;.&lt;br /&gt;
* A copy of the &#039;&#039;&#039;downstream kernel&#039;&#039;&#039;; preferably the one for your device, but you can also use the kernel from another device with the same SoC, or - as a last resort - any kernel with the relevant SoC drivers (hint: search by downstream codename).&lt;br /&gt;
* A copy of the &#039;&#039;&#039;&amp;lt;code&amp;gt;qcom_proprietary_devicetree&amp;lt;/code&amp;gt;&#039;&#039;&#039; or similar repo with the DTSI source files (because they&#039;re not in the kernel repo for whatever reason...). Search for &amp;lt;code&amp;gt;(downstream codename).dtsi&amp;lt;/code&amp;gt; on GitHub and you&#039;ll find the right repository eventually.&lt;br /&gt;
* An &#039;&#039;&#039;extracted DTB from your device&#039;&#039;&#039;. Dump this from a running device using FDT (todo: instructions, would probably be good on a generic page, maybe subpage of [[Devicetree]])?&lt;br /&gt;
* Find a similar SoC that is already supported. Usually flagship SoCs are available in mainline; try to find a flagship from around the same time as the SoC you&#039;re mainlining. Find its DTSIs as well; then you can compare the differences between downstream and mainline for the upstreamed SoC, and correlate them with differences in your SoC. You&#039;ll also be able to check the other SoC&#039;s drivers and use them as a base for your own drivers.&lt;br /&gt;
&lt;br /&gt;
== Adding the DTSI ==&lt;br /&gt;
&lt;br /&gt;
todo&lt;br /&gt;
&lt;br /&gt;
== Porting individual parts ==&lt;br /&gt;
&lt;br /&gt;
=== Clock controllers ===&lt;br /&gt;
&lt;br /&gt;
On recent Qualcomm SoCs, the downstream kernel uses the mainline Qualcomm clock driver with only &#039;&#039;some&#039;&#039; vendor-specific quirks. This means that the clock drivers and their relevant headers can pretty much be copied verbatim from downstream, with some slight modifications.&lt;br /&gt;
&lt;br /&gt;
First, create the &#039;&#039;&#039;GCC&#039;&#039;&#039; driver. Open &amp;lt;code&amp;gt;driver/clk/qcom/Kconfig&amp;lt;/code&amp;gt; and add the relevant Kconfig option for your SoC (remember to keep it ordered alphabetically):&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;kconfig&amp;quot;&amp;gt;&lt;br /&gt;
config SM_GCC_xxxx&lt;br /&gt;
	tristate &amp;quot;SMxxxx Global Clock Controller&amp;quot;&lt;br /&gt;
	depends on ARM64 || COMPILE_TEST&lt;br /&gt;
	select QCOM_GDSC&lt;br /&gt;
	help&lt;br /&gt;
	  Support for the global clock controller on SMxxxx devices.&lt;br /&gt;
	  Say Y if you want to use peripheral devices such as UART,&lt;br /&gt;
	  SPI, I2C, USB, SD/UFS, PCIe etc.&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/Makefile&amp;lt;/code&amp;gt; and add the relevant entry:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;makefile&amp;quot;&amp;gt;&lt;br /&gt;
obj-$(CONFIG_SM_GCC_xxxx) += gcc-smXXXX.o&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/gcc-smXXXX.c&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Paste the initialization code from another GCC driver (&amp;lt;syntaxhighlight inline lang=&amp;quot;c&amp;quot;&amp;gt;static struct platform_driver gcc_smXXXX_driver&amp;lt;/syntaxhighlight&amp;gt; and onwards.)&lt;br /&gt;
&lt;br /&gt;
== Porting the PMIC(s) ==&lt;br /&gt;
&lt;br /&gt;
Qualcomm devices use &#039;&#039;multiple&#039;&#039; PMICs for different purposes. Often, the PMIC is paired with an SoC or series of SoCs.&lt;br /&gt;
&lt;br /&gt;
== References ==&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Getting_started&amp;diff=101</id>
		<title>User:Knuxify/Draft:Getting started</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Getting_started&amp;diff=101"/>
		<updated>2026-01-27T05:57:51Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;This page serves as an introduction to the basics of mainlining.&lt;br /&gt;
&lt;br /&gt;
== What is mainlining? ==&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Mainlining&#039;&#039;&#039; is the act of adding support for a device, or porting its drivers from an older, non-upstream tree, to the mainline Linux kernel.&lt;br /&gt;
&lt;br /&gt;
The name comes from the term &amp;quot;&#039;&#039;mainline Linux kernel&#039;&#039;&amp;quot;, which is used to refer to the upstream Linux kernel repository maintained by Linus Torvalds&amp;lt;ref&amp;gt;https://en.wikipedia.org/wiki/Linux_kernel#Mainline_Linux&amp;lt;/ref&amp;gt;, and which itself comes from the term &amp;quot;&#039;&#039;mainline branch&#039;&#039;&amp;quot; used to refer to the main development trunk of a project&amp;lt;ref&amp;gt;https://en.wikipedia.org/wiki/Branching_(version_control)#Trunk&amp;lt;/ref&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
=== Why is mainlining necessary? ===&lt;br /&gt;
&lt;br /&gt;
Users of the Linux kernel on x86-64 PCs may be accustomed to the fact that most components work out of the box on these devices. This can be partly attributed to the fact that both AMD and Intel - the largest players in the x86-64 market - contribute support for their CPUs and chipsets directly to the mainline Linux kernel.&lt;br /&gt;
&lt;br /&gt;
With most embedded SoCs, however, the typical lifecycle of Linux support looks like this:&lt;br /&gt;
&lt;br /&gt;
* The SoC vendor forks the Linux kernel and applies patches for device support on top of this fork&lt;br /&gt;
* The SoC fork is sent to device manufacturers, who apply their own patches on top of it to add support for their devices&lt;br /&gt;
&lt;br /&gt;
The code from these forks usually never makes it back upstream; it&#039;s maintained internally by the SoC vendor&#039;s team. Yet worse, device vendors often neglect rebasing their forks on the vendor&#039;s updated kernels. As kernel APIs change over time, updating these kernels to the latest version becomes more difficult.&lt;br /&gt;
&lt;br /&gt;
Since upstreaming is not a priority, and the main goal of a vendor is to provide a viable product to developers as fast as possible, the drivers in an SoC fork don&#039;t necessarily conform to the standards and practices of the mainline Linux kernel.&lt;br /&gt;
&lt;br /&gt;
This is where &#039;&#039;&#039;mainlining&#039;&#039;&#039; comes in. Mainlining comprises of:&lt;br /&gt;
&lt;br /&gt;
* Analyzing the drivers from original source code, or experimenting with the hardware itself to determine how it works (reverse engineering), to then write new, upstream-ready drivers for it;&lt;br /&gt;
* Submitting those drivers upstream, responding to review comments, maintaining them in the mainline Linux kernel tree.&lt;br /&gt;
&lt;br /&gt;
== Prerequisites ==&lt;br /&gt;
&lt;br /&gt;
* A computer running Linux, which will handle building the kernel.&lt;br /&gt;
** If you&#039;re on Windows, you can use WSL (though flashing the kernel to your device might be a bit challenging, TODO).&lt;br /&gt;
** (Note about recommended specs goes here; faster hardware is better, but only necessary bits are rebuilt on subsequent builds; also mention ccache?)&lt;br /&gt;
* Some familiarity with the Linux shell and [[User:Knuxify/Draft:C crash course|C programming language syntax]] is recommended.&lt;br /&gt;
&lt;br /&gt;
== Getting to know your device and SoC ==&lt;br /&gt;
&lt;br /&gt;
{{todo|These are both topics worthy of their own page. Some things to mention here:&lt;br /&gt;
&lt;br /&gt;
* Finding out whether the SoC is supported to mainline and, if so, how well.&lt;br /&gt;
* Finding out what components your device has (it&#039;s nice to keep a table!)}}&lt;br /&gt;
&lt;br /&gt;
== Preparing the build environment ==&lt;br /&gt;
&lt;br /&gt;
In order to mainline a device, we need to be able to cross-compile the Linux kernel for it.&lt;br /&gt;
&lt;br /&gt;
=== Downloading the Linux kernel source code ===&lt;br /&gt;
&lt;br /&gt;
Depending on your SoC&#039;s support status:&lt;br /&gt;
&lt;br /&gt;
* There may be an up-to-date maintained [[close-to mainline]] fork of the Linux kernel for your device&#039;s SoC; if there is one, start from it.&lt;br /&gt;
* If there is no dedicated fork for your device&#039;s SoC, or the fork is out of date, start with either:&lt;br /&gt;
** &#039;&#039;&#039;The latest stable tag&#039;&#039;&#039; directly from Torvalds&#039; tree (see [https://web.git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/] or &amp;lt;code&amp;gt;github.com/torvalds/linux&amp;lt;/code&amp;gt;).&lt;br /&gt;
** For very new SoCs with ongoing work, you may want to use the &#039;&#039;&#039;linux-next tree&#039;&#039;&#039; instead.&lt;br /&gt;
&lt;br /&gt;
If you&#039;re on GitHub, you can fork [https://github.com/torvalds/linux the torvalds/linux repository] and start from there.&lt;br /&gt;
&lt;br /&gt;
Once you have your kernel cloned, switch to the latest tag, then create a new feature branch from it:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ git checkout v6.14  # replace 6.14 with latest kernel version&lt;br /&gt;
$ git checkout -b codename-mainline  # git checkout -b creates a new branch based on current HEAD and checks out into it&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
{{todo|Link to some nice guide on git here (and probably elsewhere in the page)}}&lt;br /&gt;
&lt;br /&gt;
=== Cross-compiler setup ===&lt;br /&gt;
&lt;br /&gt;
{{todo|Explain cross-compiler setup; where to get toolchains (AUR for Arch users? Linaro?), postmarketOS envkernel.sh}}&lt;br /&gt;
&lt;br /&gt;
=== Selecting/creating a defconfig ===&lt;br /&gt;
&lt;br /&gt;
The &#039;&#039;&#039;kernel config&#039;&#039;&#039; dictates which drivers and platform-specific support bits (including DTBs) get built. There are a handful of pre-made configs, called &#039;&#039;&#039;defconfigs&#039;&#039;&#039;, in &amp;lt;code&amp;gt;arch/{arm,arm64,...}/configs&amp;lt;/code&amp;gt; - use &amp;lt;code&amp;gt;make name_defconfig&amp;lt;/code&amp;gt; to build them.&lt;br /&gt;
&lt;br /&gt;
{{todo|Common ARM(64) config? Which options to select/unselect? pmbootstrap kconfig check might be useful here}}&lt;br /&gt;
&lt;br /&gt;
=== Adding a device tree for your device ===&lt;br /&gt;
&lt;br /&gt;
Devices using ARM chipsets use [[devicetree]]s to describe the hardware. See [[Devicetree/Writing a Linux device tree]] for a guide.&lt;br /&gt;
&lt;br /&gt;
=== Building the kernel ===&lt;br /&gt;
&lt;br /&gt;
{{todo|&amp;lt;code&amp;gt;make -j$(nproc)&amp;lt;/code&amp;gt;}}&lt;br /&gt;
&lt;br /&gt;
=== Packaging the kernel into a boot image ===&lt;br /&gt;
&lt;br /&gt;
{{todo|See how I do it in [https://github.com/refractionware/linux/blob/meta/tools/mainline-tools mainline-tools], mention pmbootstrap build --envkernel?}}&lt;br /&gt;
&lt;br /&gt;
Then, flash the resulting kernel to the device.&lt;br /&gt;
&lt;br /&gt;
== Getting the kernel to boot ==&lt;br /&gt;
&lt;br /&gt;
{{todo|UART, DTBO trickery}}&lt;br /&gt;
&lt;br /&gt;
== See also ==&lt;br /&gt;
&lt;br /&gt;
{{todo|pmOS wiki has links to talks and resources}}&lt;br /&gt;
&lt;br /&gt;
== References ==&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=100</id>
		<title>User:Knuxify/Draft:Qualcomm/Adding a new SoC to mainline Linux</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=100"/>
		<updated>2025-07-14T16:18:47Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: /* Finding information about your SoC */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Subpage of|Qualcomm}}&lt;br /&gt;
{{Work-in-progress page|note=Currently in the middle of finding this out in real time :)}}&lt;br /&gt;
&lt;br /&gt;
This guide will cover the process of adding support for a recent (~2020 or newer, todo?) Qualcomm SoC into mainline Linux. Most of the information contained within is also applicable to older chips, though more manual effort may be needed to get these to run. &amp;lt;!--For the U-Boot guide, see TODO.--&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This guide was tested with the SM7435. Some details might be different for other SoCs. If you have any hints, please contribute!&lt;br /&gt;
&lt;br /&gt;
== High-level overview ==&lt;br /&gt;
&lt;br /&gt;
{{todo|Some of this will have to be moved out to the top-level Qualcomm page}}&lt;br /&gt;
&lt;br /&gt;
The basic components of a Qualcomm SoC are:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;GCC&#039;&#039;&#039;, or &#039;&#039;Global Clock Controller&#039;&#039;; as the name suggests, it is the primary clock controller for most components.&lt;br /&gt;
* The other clock controllers: &#039;&#039;&#039;CAMCC&#039;&#039;&#039;, &#039;&#039;&#039;DISPCC&#039;&#039;&#039;, &#039;&#039;&#039;GPUCC&#039;&#039;&#039; and &#039;&#039;&#039;VIDEOCC&#039;&#039;&#039;.&lt;br /&gt;
* The &#039;&#039;&#039;RPM&#039;&#039;&#039;, or &#039;&#039;Resource and Power Manager&#039;&#039; (&#039;&#039;&#039;RPMH&#039;&#039;&#039; or RPM &#039;&#039;Hardened&#039;&#039; in SDM845 and later); todo explanation from [https://wiki.postmarketos.org/wiki/Qualcomm_Glossary qcom glossary].&lt;br /&gt;
** Under the RPM is the &#039;&#039;&#039;RPM(H)CC&#039;&#039;&#039; (&#039;&#039;RPM clock controller&#039;&#039;) and &#039;&#039;&#039;RPM(H)PD&#039;&#039;&#039; (&#039;&#039;RPM power domains&#039;&#039;).&lt;br /&gt;
* &#039;&#039;&#039;QUP&#039;&#039;&#039;, or &#039;&#039;Qualcomm Universal Peripheral&#039;&#039;; the part of the SoC that provides I2C or SPI busses, as well as UART.&lt;br /&gt;
* &#039;&#039;&#039;TLMM&#039;&#039;&#039; (&#039;&#039;Top Level Mode Multiplexer&#039;&#039;); provides pinmux and GPIO pins.&lt;br /&gt;
* Many &#039;&#039;&#039;NOC&#039;&#039;&#039; interconnects (&#039;&#039;Network on Chip&#039;&#039;).&lt;br /&gt;
* A timer and an interrupt controller, both standard ARM parts.&lt;br /&gt;
&lt;br /&gt;
These are just the most low-level components; from there, we can move on to the higher-level ones:&lt;br /&gt;
&lt;br /&gt;
* Thermal monitoring sensor&lt;br /&gt;
* USB host controller and PHY&lt;br /&gt;
* Display controller and DSI PHY&lt;br /&gt;
* GPU&lt;br /&gt;
* etc.&lt;br /&gt;
&lt;br /&gt;
This page will touch on mainline porting of most of these parts.&lt;br /&gt;
&lt;br /&gt;
== Finding information about your SoC ==&lt;br /&gt;
&lt;br /&gt;
In order to begin mainlining your SoC, you need to have the following bits of information:&lt;br /&gt;
&lt;br /&gt;
* The codename of your SoC. If you&#039;re lucky, it&#039;s probably already somewhere out there online. This will be useful when looking things up in the downstream kernel, as it primarily uses the codename, whereas mainline uses the model number. (TODO - we should have a table of SoC codenames somewhere!)&lt;br /&gt;
* A copy of the downstream kernel; preferably the one for your device, but you can also use the kernel from another device with the same SoC, or - as a last resort - any kernel with the relevant SoC drivers (hint: search by codename).&lt;br /&gt;
* A copy of the &amp;lt;code&amp;gt;qcom_proprietary_devicetree&amp;lt;/code&amp;gt; or similar repo with the DTSI source files (because they&#039;re not in the kernel repo for whatever reason...). Search for &amp;lt;code&amp;gt;(codename).dtsi&amp;lt;/code&amp;gt; on GitHub and you&#039;ll find the right repository eventually.&lt;br /&gt;
* An extracted DTB from your device. Dump this from a running device using FDT (todo: instructions, would probably be good on a generic page, maybe subpage of [[Devicetree]]?&lt;br /&gt;
* Find a similar SoC that is already supported. Usually flagship SoCs are available in mainline; try to find a flagship from around the same time as the SoC you&#039;re mainlining. Find its DTSIs as well; then you can compare the differences between downstream and mainline for the upstreamed SoC, and correlate them with differences in your SoC. You&#039;ll also be able to check the other SoC&#039;s drivers and use them as a base for your own drivers.&lt;br /&gt;
&lt;br /&gt;
== Adding the DTSI ==&lt;br /&gt;
&lt;br /&gt;
todo&lt;br /&gt;
&lt;br /&gt;
== Porting individual parts ==&lt;br /&gt;
&lt;br /&gt;
=== Clock controllers ===&lt;br /&gt;
&lt;br /&gt;
On recent Qualcomm SoCs, the downstream kernel uses the mainline Qualcomm clock driver with only &#039;&#039;some&#039;&#039; vendor-specific quirks. This means that the clock drivers and their relevant headers can pretty much be copied verbatim from downstream, with some slight modifications.&lt;br /&gt;
&lt;br /&gt;
First, create the &#039;&#039;&#039;GCC&#039;&#039;&#039; driver. Open &amp;lt;code&amp;gt;driver/clk/qcom/Kconfig&amp;lt;/code&amp;gt; and add the relevant Kconfig option for your SoC (remember to keep it ordered alphabetically):&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;kconfig&amp;quot;&amp;gt;&lt;br /&gt;
config SM_GCC_xxxx&lt;br /&gt;
	tristate &amp;quot;SMxxxx Global Clock Controller&amp;quot;&lt;br /&gt;
	depends on ARM64 || COMPILE_TEST&lt;br /&gt;
	select QCOM_GDSC&lt;br /&gt;
	help&lt;br /&gt;
	  Support for the global clock controller on SMxxxx devices.&lt;br /&gt;
	  Say Y if you want to use peripheral devices such as UART,&lt;br /&gt;
	  SPI, I2C, USB, SD/UFS, PCIe etc.&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/Makefile&amp;lt;/code&amp;gt; and add the relevant entry:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;makefile&amp;quot;&amp;gt;&lt;br /&gt;
obj-$(CONFIG_SM_GCC_xxxx) += gcc-smXXXX.o&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/gcc-smXXXX.c&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Paste the initialization code from another GCC driver (&amp;lt;syntaxhighlight inline lang=&amp;quot;c&amp;quot;&amp;gt;static struct platform_driver gcc_smXXXX_driver&amp;lt;/syntaxhighlight&amp;gt; and onwards.)&lt;br /&gt;
&lt;br /&gt;
== Porting the PMIC(s) ==&lt;br /&gt;
&lt;br /&gt;
Qualcomm devices use &#039;&#039;multiple&#039;&#039; PMICs for different purposes. Often, the PMIC is paired with an SoC or series of SoCs.&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=99</id>
		<title>User:Knuxify/Draft:Qualcomm/Adding a new SoC to mainline Linux</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=99"/>
		<updated>2025-07-14T16:17:35Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Subpage of|Qualcomm}}&lt;br /&gt;
{{Work-in-progress page|note=Currently in the middle of finding this out in real time :)}}&lt;br /&gt;
&lt;br /&gt;
This guide will cover the process of adding support for a recent (~2020 or newer, todo?) Qualcomm SoC into mainline Linux. Most of the information contained within is also applicable to older chips, though more manual effort may be needed to get these to run. &amp;lt;!--For the U-Boot guide, see TODO.--&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This guide was tested with the SM7435. Some details might be different for other SoCs. If you have any hints, please contribute!&lt;br /&gt;
&lt;br /&gt;
== High-level overview ==&lt;br /&gt;
&lt;br /&gt;
{{todo|Some of this will have to be moved out to the top-level Qualcomm page}}&lt;br /&gt;
&lt;br /&gt;
The basic components of a Qualcomm SoC are:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;GCC&#039;&#039;&#039;, or &#039;&#039;Global Clock Controller&#039;&#039;; as the name suggests, it is the primary clock controller for most components.&lt;br /&gt;
* The other clock controllers: &#039;&#039;&#039;CAMCC&#039;&#039;&#039;, &#039;&#039;&#039;DISPCC&#039;&#039;&#039;, &#039;&#039;&#039;GPUCC&#039;&#039;&#039; and &#039;&#039;&#039;VIDEOCC&#039;&#039;&#039;.&lt;br /&gt;
* The &#039;&#039;&#039;RPM&#039;&#039;&#039;, or &#039;&#039;Resource and Power Manager&#039;&#039; (&#039;&#039;&#039;RPMH&#039;&#039;&#039; or RPM &#039;&#039;Hardened&#039;&#039; in SDM845 and later); todo explanation from [https://wiki.postmarketos.org/wiki/Qualcomm_Glossary qcom glossary].&lt;br /&gt;
** Under the RPM is the &#039;&#039;&#039;RPM(H)CC&#039;&#039;&#039; (&#039;&#039;RPM clock controller&#039;&#039;) and &#039;&#039;&#039;RPM(H)PD&#039;&#039;&#039; (&#039;&#039;RPM power domains&#039;&#039;).&lt;br /&gt;
* &#039;&#039;&#039;QUP&#039;&#039;&#039;, or &#039;&#039;Qualcomm Universal Peripheral&#039;&#039;; the part of the SoC that provides I2C or SPI busses, as well as UART.&lt;br /&gt;
* &#039;&#039;&#039;TLMM&#039;&#039;&#039; (&#039;&#039;Top Level Mode Multiplexer&#039;&#039;); provides pinmux and GPIO pins.&lt;br /&gt;
* Many &#039;&#039;&#039;NOC&#039;&#039;&#039; interconnects (&#039;&#039;Network on Chip&#039;&#039;).&lt;br /&gt;
* A timer and an interrupt controller, both standard ARM parts.&lt;br /&gt;
&lt;br /&gt;
These are just the most low-level components; from there, we can move on to the higher-level ones:&lt;br /&gt;
&lt;br /&gt;
* Thermal monitoring sensor&lt;br /&gt;
* USB host controller and PHY&lt;br /&gt;
* Display controller and DSI PHY&lt;br /&gt;
* GPU&lt;br /&gt;
* etc.&lt;br /&gt;
&lt;br /&gt;
This page will touch on mainline porting of most of these parts.&lt;br /&gt;
&lt;br /&gt;
== Finding information about your SoC ==&lt;br /&gt;
&lt;br /&gt;
In order to begin mainlining your SoC, you need to have the following bits of information:&lt;br /&gt;
&lt;br /&gt;
* The codename of your SoC. If you&#039;re lucky, it&#039;s probably already somewhere out there online. This will be useful when looking things up in the downstream kernel, as it primarily uses the codename, whereas mainline uses the model number. (TODO - we should have a table of SoC codenames somewhere!)&lt;br /&gt;
* A copy of the downstream kernel; preferably the one for your device, but you can also use the kernel from another device with the same SoC, or - as a last resort - any kernel with the relevant SoC drivers (hint: search by codename).&lt;br /&gt;
* A copy of the &amp;lt;code&amp;gt;qcom_proprietary_devicetree&amp;lt;/code&amp;gt; or similar repo with the DTSI source files (because they&#039;re not in the kernel repo for whatever reason...). Search for &amp;lt;code&amp;gt;(codename).dtsi&amp;lt;/code&amp;gt; on GitHub and you&#039;ll find the right repository eventually.&lt;br /&gt;
* An extracted DTB from your device. Dump this from a running device using FDT (todo: instructions, would probably be good on a generic page, maybe subpage of [[Devicetree]]?&lt;br /&gt;
* Find a similar SoC that is already supported. Usually flagship SoCs are available in mainline; try to find a flagship from around the same time as the SoC you&#039;re mainlining. Find its DTSIs as well; then you can compare the differences between downstream and mainline for the upstreamed SoC, and correlate them with differences in your SoC.&lt;br /&gt;
&lt;br /&gt;
== Adding the DTSI ==&lt;br /&gt;
&lt;br /&gt;
todo&lt;br /&gt;
&lt;br /&gt;
== Porting individual parts ==&lt;br /&gt;
&lt;br /&gt;
=== Clock controllers ===&lt;br /&gt;
&lt;br /&gt;
On recent Qualcomm SoCs, the downstream kernel uses the mainline Qualcomm clock driver with only &#039;&#039;some&#039;&#039; vendor-specific quirks. This means that the clock drivers and their relevant headers can pretty much be copied verbatim from downstream, with some slight modifications.&lt;br /&gt;
&lt;br /&gt;
First, create the &#039;&#039;&#039;GCC&#039;&#039;&#039; driver. Open &amp;lt;code&amp;gt;driver/clk/qcom/Kconfig&amp;lt;/code&amp;gt; and add the relevant Kconfig option for your SoC (remember to keep it ordered alphabetically):&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;kconfig&amp;quot;&amp;gt;&lt;br /&gt;
config SM_GCC_xxxx&lt;br /&gt;
	tristate &amp;quot;SMxxxx Global Clock Controller&amp;quot;&lt;br /&gt;
	depends on ARM64 || COMPILE_TEST&lt;br /&gt;
	select QCOM_GDSC&lt;br /&gt;
	help&lt;br /&gt;
	  Support for the global clock controller on SMxxxx devices.&lt;br /&gt;
	  Say Y if you want to use peripheral devices such as UART,&lt;br /&gt;
	  SPI, I2C, USB, SD/UFS, PCIe etc.&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/Makefile&amp;lt;/code&amp;gt; and add the relevant entry:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;makefile&amp;quot;&amp;gt;&lt;br /&gt;
obj-$(CONFIG_SM_GCC_xxxx) += gcc-smXXXX.o&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Open &amp;lt;code&amp;gt;driver/clk/qcom/gcc-smXXXX.c&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
Paste the initialization code from another GCC driver (&amp;lt;syntaxhighlight inline lang=&amp;quot;c&amp;quot;&amp;gt;static struct platform_driver gcc_smXXXX_driver&amp;lt;/syntaxhighlight&amp;gt; and onwards.)&lt;br /&gt;
&lt;br /&gt;
== Porting the PMIC(s) ==&lt;br /&gt;
&lt;br /&gt;
Qualcomm devices use &#039;&#039;multiple&#039;&#039; PMICs for different purposes. Often, the PMIC is paired with an SoC or series of SoCs.&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=98</id>
		<title>User:Knuxify/Draft:Qualcomm/Adding a new SoC to mainline Linux</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Qualcomm/Adding_a_new_SoC_to_mainline_Linux&amp;diff=98"/>
		<updated>2025-07-13T16:24:44Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Created page with &amp;quot;{{Subpage of|Qualcomm}} {{Work-in-progress page|note=Currently in the middle of finding this out in real time :)}}  This guide will cover the process of adding support for a recent (~2020 or newer, todo?) Qualcomm SoC into mainline Linux. Most of the information contained within is also applicable to older chips, though more manual effort may be needed to get these to run. &amp;lt;!--For the U-Boot guide, see TODO.--&amp;gt;  == High-level overview ==  {{todo|Some of this will have to...&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Subpage of|Qualcomm}}&lt;br /&gt;
{{Work-in-progress page|note=Currently in the middle of finding this out in real time :)}}&lt;br /&gt;
&lt;br /&gt;
This guide will cover the process of adding support for a recent (~2020 or newer, todo?) Qualcomm SoC into mainline Linux. Most of the information contained within is also applicable to older chips, though more manual effort may be needed to get these to run. &amp;lt;!--For the U-Boot guide, see TODO.--&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== High-level overview ==&lt;br /&gt;
&lt;br /&gt;
{{todo|Some of this will have to be moved out to the top-level Qualcomm page}}&lt;br /&gt;
&lt;br /&gt;
The basic components of a Qualcomm SoC are:&lt;br /&gt;
&lt;br /&gt;
* The &#039;&#039;&#039;GCC&#039;&#039;&#039;, or &#039;&#039;Global Clock Controller&#039;&#039;; as the name suggests, it is the primary clock controller for most components.&lt;br /&gt;
* The other clock controllers: &#039;&#039;&#039;CAMCC&#039;&#039;&#039;, &#039;&#039;&#039;DISPCC&#039;&#039;&#039;, &#039;&#039;&#039;GPUCC&#039;&#039;&#039; and &#039;&#039;&#039;VIDEOCC&#039;&#039;&#039;.&lt;br /&gt;
* The &#039;&#039;&#039;RPM&#039;&#039;&#039;, or &#039;&#039;Resource and Power Manager&#039;&#039; (&#039;&#039;&#039;RPMH&#039;&#039;&#039; or RPM &#039;&#039;Hardened&#039;&#039; in SDM845 and later); todo explanation from [https://wiki.postmarketos.org/wiki/Qualcomm_Glossary qcom glossary].&lt;br /&gt;
** Under the RPM is the &#039;&#039;&#039;RPM(H)CC&#039;&#039;&#039; (&#039;&#039;RPM clock controller&#039;&#039;) and &#039;&#039;&#039;RPM(H)PD&#039;&#039;&#039; (&#039;&#039;RPM power domains&#039;&#039;).&lt;br /&gt;
* &#039;&#039;&#039;QUP&#039;&#039;&#039;, or &#039;&#039;Qualcomm Universal Peripheral&#039;&#039;; the part of the SoC that provides I2C or SPI busses, as well as UART.&lt;br /&gt;
* &#039;&#039;&#039;TLMM&#039;&#039;&#039; (&#039;&#039;Top Level Mode Multiplexer&#039;&#039;); provides pinmux and GPIO pins.&lt;br /&gt;
* Many &#039;&#039;&#039;NOC&#039;&#039;&#039; interconnects (&#039;&#039;Network on Chip&#039;&#039;).&lt;br /&gt;
* A timer and an interrupt controller, both standard ARM parts.&lt;br /&gt;
&lt;br /&gt;
These are just the most low-level components; from there, we can move on to the higher-level ones:&lt;br /&gt;
&lt;br /&gt;
* Thermal monitoring sensor&lt;br /&gt;
* USB host controller and PHY&lt;br /&gt;
* Display controller and DSI PHY&lt;br /&gt;
* GPU&lt;br /&gt;
* etc.&lt;br /&gt;
&lt;br /&gt;
This page will touch on mainline porting of most of these parts.&lt;br /&gt;
&lt;br /&gt;
== Finding information about your SoC ==&lt;br /&gt;
&lt;br /&gt;
In order to begin mainlining your SoC, you need to have the following bits of information:&lt;br /&gt;
&lt;br /&gt;
* The codename of your SoC. If you&#039;re lucky, it&#039;s probably already somewhere out there online. This will be useful when looking things up in the downstream kernel, as it primarily uses the codename, whereas mainline uses the model number. (TODO - we should have a table of SoC codenames somewhere!)&lt;br /&gt;
* A copy of the downstream kernel; preferably the one for your device, but you can also use the kernel from another device with the same SoC, or - as a last resort - any kernel with the relevant SoC drivers (hint: search by codename).&lt;br /&gt;
* A copy of the &amp;lt;code&amp;gt;qcom_proprietary_devicetree&amp;lt;/code&amp;gt; or similar repo with the DTSI source files (because they&#039;re not in the kernel repo for whatever reason...). Search for &amp;lt;code&amp;gt;(codename).dtsi&amp;lt;/code&amp;gt; on GitHub and you&#039;ll find the right repository eventually.&lt;br /&gt;
* An extracted DTB from your device. Dump this from a running device using FDT&lt;br /&gt;
&lt;br /&gt;
== Porting individual parts ==&lt;br /&gt;
&lt;br /&gt;
=== Clock controllers ===&lt;br /&gt;
&lt;br /&gt;
On recent Qualcomm SoCs, the downstream kernel uses the mainline Qualcomm clock driver with only &#039;&#039;some&#039;&#039; vendor-specific quirks. This means that the clock drivers and their relevant headers can pretty much be copied verbatim from downstream, with some slight modifications.&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Subpage_of&amp;diff=97</id>
		<title>Template:Subpage of</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Subpage_of&amp;diff=97"/>
		<updated>2025-07-13T07:45:54Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Created page with &amp;quot;&amp;lt;noinclude&amp;gt;&amp;lt;templatedata&amp;gt; { 	&amp;quot;params&amp;quot;: { 		&amp;quot;1&amp;quot;: { 			&amp;quot;label&amp;quot;: &amp;quot;First-level page&amp;quot;, 			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;, 			&amp;quot;required&amp;quot;: true 		}, 		&amp;quot;2&amp;quot;: { 			&amp;quot;label&amp;quot;: &amp;quot;Second level page&amp;quot;, 			&amp;quot;description&amp;quot;: &amp;quot;The page title after the first slash (/).&amp;quot;, 			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot; 		}, 		&amp;quot;3&amp;quot;: { 			&amp;quot;label&amp;quot;: &amp;quot;Third-level page&amp;quot;, 			&amp;quot;description&amp;quot;: &amp;quot;The page title after the second slash (/).&amp;quot;, 			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot; 		} 	}, 	&amp;quot;description&amp;quot;: &amp;quot;Displays a link back to the parent page of a subpage. Include this...&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;noinclude&amp;gt;&amp;lt;templatedata&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
	&amp;quot;params&amp;quot;: {&lt;br /&gt;
		&amp;quot;1&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;First-level page&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;required&amp;quot;: true&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;2&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Second level page&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;The page title after the first slash (/).&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;3&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Third-level page&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;The page title after the second slash (/).&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;&lt;br /&gt;
		}&lt;br /&gt;
	},&lt;br /&gt;
	&amp;quot;description&amp;quot;: &amp;quot;Displays a link back to the parent page of a subpage. Include this template at the beginning of a page.&amp;quot;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/templatedata&amp;gt;&lt;br /&gt;
This is intended to replace MediaWiki&#039;s default subpage link display feature, which is not enabled on the pmOS wiki (as it would interfere with the names of any wiki page that uses the / character).&lt;br /&gt;
&lt;br /&gt;
This template supports up to 3 subpages.&lt;br /&gt;
&lt;br /&gt;
== Example ==&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;{{Subpage of|Qualcomm}}&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
{{Subpage of|Qualcomm}}&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;{{Subpage of|Qualcomm|Adding a new SoC to mainline Linux}}&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
{{Subpage of|Qualcomm|Adding a new SoC to mainline Linux}}&lt;br /&gt;
&amp;lt;/noinclude&amp;gt;&amp;lt;includeonly&amp;gt;&amp;lt;div id=&amp;quot;contentSub&amp;quot; style=&amp;quot;margin-top: -8px; margin-bottom: 18px;&amp;quot;&amp;gt;&amp;lt;span class=&amp;quot;subpages&amp;quot;&amp;gt;&amp;amp;lt; [[{{{1}}}]]{{#if: {{{2|}}}|&amp;amp;nbsp;&amp;amp;#124; [[{{{1}}}/{{{2}}}|{{{2}}}]]|}}{{#if: {{{3|}}}|&amp;amp;nbsp;&amp;amp;#124;[[{{{1}}}/{{{2}}}/{{{3}}}|{{{3}}}]]|}}&amp;lt;/span&amp;gt;‎&amp;lt;/div&amp;gt;&amp;lt;/includeonly&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Category:Work-in-progress_pages&amp;diff=96</id>
		<title>Category:Work-in-progress pages</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Category:Work-in-progress_pages&amp;diff=96"/>
		<updated>2025-07-13T07:40:58Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Created page with &amp;quot;Pages which are marked as work-in-progress using the &amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;{{Work-in-progress page}}&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt; template.&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;Pages which are marked as work-in-progress using the [[Template:Work-in-progress page|&amp;lt;code&amp;gt;&amp;lt;nowiki&amp;gt;{{Work-in-progress page}}&amp;lt;/nowiki&amp;gt;&amp;lt;/code&amp;gt;]] template.&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Work-in-progress_page&amp;diff=95</id>
		<title>Template:Work-in-progress page</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Work-in-progress_page&amp;diff=95"/>
		<updated>2025-07-13T07:40:07Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;noinclude&amp;gt;&lt;br /&gt;
&amp;lt;templatedata&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
	&amp;quot;params&amp;quot;: {&lt;br /&gt;
		&amp;quot;note&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Note&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;A note to display in the box.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;content&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;nocategory&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Do not add to \&amp;quot;Stub pages\&amp;quot; category&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;If set, the page will not be added to the \&amp;quot;Stub pages\&amp;quot; category.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;boolean&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;no&amp;quot;&lt;br /&gt;
		}&lt;br /&gt;
	},&lt;br /&gt;
	&amp;quot;format&amp;quot;: &amp;quot;inline&amp;quot;,&lt;br /&gt;
	&amp;quot;description&amp;quot;: &amp;quot;Template to include on WIP pages to warn the user and give additional details as to what&#039;s currently in progress.&amp;quot;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/templatedata&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Usage ==&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&amp;lt;nowiki&amp;gt;{{Work-in-progress_page|note=Add some notes about foo, clean up section about bar}}&lt;br /&gt;
&amp;lt;/nowiki&amp;gt;&amp;lt;/pre&amp;gt;&lt;br /&gt;
{{Work-in-progress_page|note=Add some notes about foo, clean up section about bar|nocategory=yes}}&lt;br /&gt;
&lt;br /&gt;
Pages are added to [[:Category:Work-in-progress pages]] by default. To prevent that add the &amp;lt;code&amp;gt;nocategory=yes&amp;lt;/code&amp;gt; argument:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&amp;lt;nowiki&amp;gt;{{Work-in-progress_page|note=Add some notes about foo, clean up section about bar|nocategory=yes}}&lt;br /&gt;
&amp;lt;/nowiki&amp;gt;&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;/noinclude&amp;gt;&amp;lt;includeonly&amp;gt;{{Icon box&lt;br /&gt;
| box-icons = 🚧&lt;br /&gt;
| box-text = &#039;&#039;&#039;This page is a work-in-progress.&#039;&#039;&#039; Some information contained within may be inaccurate or incomplete.&lt;br /&gt;
{{#if: {{{note|{{{1|}}}}}}|&amp;lt;br&amp;gt;In particular: &#039;&#039;{{{note|{{{1|}}}}}}&#039;&#039;|}}&lt;br /&gt;
| border-color = #C1B598&lt;br /&gt;
| border-width = 2px&lt;br /&gt;
| border-style = dotted&lt;br /&gt;
| background = #E8E0CC&lt;br /&gt;
| background-dark = #221e16&lt;br /&gt;
| class = box-wip&lt;br /&gt;
}}{{#ifeq: {{boolean|{{{nocategory|no}}}|default=false}}|false|[[Category:Work-in-progress pages]]|}}&amp;lt;/includeonly&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Work-in-progress_page&amp;diff=94</id>
		<title>Template:Work-in-progress page</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Work-in-progress_page&amp;diff=94"/>
		<updated>2025-07-13T07:40:00Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Created page with &amp;quot;&amp;lt;noinclude&amp;gt; {{Template}} &amp;lt;templatedata&amp;gt; { 	&amp;quot;params&amp;quot;: { 		&amp;quot;note&amp;quot;: { 			&amp;quot;label&amp;quot;: &amp;quot;Note&amp;quot;, 			&amp;quot;description&amp;quot;: &amp;quot;A note to display in the box.&amp;quot;, 			&amp;quot;type&amp;quot;: &amp;quot;content&amp;quot; 		}, 		&amp;quot;nocategory&amp;quot;: { 			&amp;quot;label&amp;quot;: &amp;quot;Do not add to \&amp;quot;Stub pages\&amp;quot; category&amp;quot;, 			&amp;quot;description&amp;quot;: &amp;quot;If set, the page will not be added to the \&amp;quot;Stub pages\&amp;quot; category.&amp;quot;, 			&amp;quot;type&amp;quot;: &amp;quot;boolean&amp;quot;, 			&amp;quot;autovalue&amp;quot;: &amp;quot;no&amp;quot; 		} 	}, 	&amp;quot;format&amp;quot;: &amp;quot;inline&amp;quot;, 	&amp;quot;description&amp;quot;: &amp;quot;Template to include on WIP pages to warn the user and give addi...&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;noinclude&amp;gt;&lt;br /&gt;
{{Template}}&lt;br /&gt;
&amp;lt;templatedata&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
	&amp;quot;params&amp;quot;: {&lt;br /&gt;
		&amp;quot;note&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Note&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;A note to display in the box.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;content&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;nocategory&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Do not add to \&amp;quot;Stub pages\&amp;quot; category&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;If set, the page will not be added to the \&amp;quot;Stub pages\&amp;quot; category.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;boolean&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;no&amp;quot;&lt;br /&gt;
		}&lt;br /&gt;
	},&lt;br /&gt;
	&amp;quot;format&amp;quot;: &amp;quot;inline&amp;quot;,&lt;br /&gt;
	&amp;quot;description&amp;quot;: &amp;quot;Template to include on WIP pages to warn the user and give additional details as to what&#039;s currently in progress.&amp;quot;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/templatedata&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Usage ==&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&amp;lt;nowiki&amp;gt;{{Work-in-progress_page|note=Add some notes about foo, clean up section about bar}}&lt;br /&gt;
&amp;lt;/nowiki&amp;gt;&amp;lt;/pre&amp;gt;&lt;br /&gt;
{{Work-in-progress_page|note=Add some notes about foo, clean up section about bar|nocategory=yes}}&lt;br /&gt;
&lt;br /&gt;
Pages are added to [[:Category:Work-in-progress pages]] by default. To prevent that add the &amp;lt;code&amp;gt;nocategory=yes&amp;lt;/code&amp;gt; argument:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&amp;lt;nowiki&amp;gt;{{Work-in-progress_page|note=Add some notes about foo, clean up section about bar|nocategory=yes}}&lt;br /&gt;
&amp;lt;/nowiki&amp;gt;&amp;lt;/pre&amp;gt;&lt;br /&gt;
&amp;lt;/noinclude&amp;gt;&amp;lt;includeonly&amp;gt;{{Icon box&lt;br /&gt;
| box-icons = 🚧&lt;br /&gt;
| box-text = &#039;&#039;&#039;This page is a work-in-progress.&#039;&#039;&#039; Some information contained within may be inaccurate or incomplete.&lt;br /&gt;
{{#if: {{{note|{{{1|}}}}}}|&amp;lt;br&amp;gt;In particular: &#039;&#039;{{{note|{{{1|}}}}}}&#039;&#039;|}}&lt;br /&gt;
| border-color = #C1B598&lt;br /&gt;
| border-width = 2px&lt;br /&gt;
| border-style = dotted&lt;br /&gt;
| background = #E8E0CC&lt;br /&gt;
| background-dark = #221e16&lt;br /&gt;
| class = box-wip&lt;br /&gt;
}}{{#ifeq: {{boolean|{{{nocategory|no}}}|default=false}}|false|[[Category:Work-in-progress pages]]|}}&amp;lt;/includeonly&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Boolean&amp;diff=91</id>
		<title>Template:Boolean</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Boolean&amp;diff=91"/>
		<updated>2025-03-02T07:45:18Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;includeonly&amp;gt;{{#switch: {{lc: {{#if: {{{value|}}}|{{{value}}}|{{#if: {{{1|}}}|{{{1}}}|{{{default|false}}}}}}}}}&lt;br /&gt;
|1|y|yes|t|true=true&lt;br /&gt;
|0|n|no|f|false=false&lt;br /&gt;
|{{#if: {{{default-invalid|false}}}|{{{boolean|{{{default-invalid|false}}}}}}||}}&lt;br /&gt;
}}&amp;lt;/includeonly&amp;gt;&amp;lt;!--&lt;br /&gt;
&lt;br /&gt;
--&amp;gt;&amp;lt;noinclude&amp;gt;&lt;br /&gt;
&amp;lt;templatedata&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
	&amp;quot;params&amp;quot;: {&lt;br /&gt;
		&amp;quot;1&amp;quot;: {&lt;br /&gt;
			&amp;quot;aliases&amp;quot;: [&lt;br /&gt;
				&amp;quot;value&amp;quot;&lt;br /&gt;
			],&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Value&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Value to turn into a boolean. \&amp;quot;1\&amp;quot;, \&amp;quot;y\&amp;quot;, \&amp;quot;yes\&amp;quot;, \&amp;quot;t\&amp;quot; or \&amp;quot;true\&amp;quot; will turn into \&amp;quot;true\&amp;quot;; \&amp;quot;0\&amp;quot;, \&amp;quot;n\&amp;quot;, \&amp;quot;no\&amp;quot;, \&amp;quot;f\&amp;quot; or \&amp;quot;false\&amp;quot; will turn into \&amp;quot;false\&amp;quot;. Case insensitive.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;boolean&amp;quot;,&lt;br /&gt;
			&amp;quot;suggested&amp;quot;: true&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;default&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Default&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Default value to fall back to if the passed value is empty. Accepts the same values as the value parameter.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;boolean&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;false&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;default-invalid&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Default for invalid values&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Default value for invalid values. Accepts the same values as the \&amp;quot;values\&amp;quot; parameter, or an empty string.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;boolean&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;false&amp;quot;&lt;br /&gt;
		}&lt;br /&gt;
	},&lt;br /&gt;
	&amp;quot;description&amp;quot;: &amp;quot;Parse a boolean argument (\&amp;quot;y\&amp;quot;, \&amp;quot;yes\&amp;quot;, \&amp;quot;1\&amp;quot;, \&amp;quot;true\&amp;quot;, \&amp;quot;t\&amp;quot;; \&amp;quot;n\&amp;quot;, \&amp;quot;no\&amp;quot;, \&amp;quot;0\&amp;quot;, \&amp;quot;false\&amp;quot;, \&amp;quot;f\&amp;quot;) and turn it into either \&amp;quot;true\&amp;quot; or \&amp;quot;false\&amp;quot;.&amp;quot;,&lt;br /&gt;
	&amp;quot;paramOrder&amp;quot;: [&lt;br /&gt;
		&amp;quot;1&amp;quot;,&lt;br /&gt;
		&amp;quot;default&amp;quot;,&lt;br /&gt;
		&amp;quot;default-invalid&amp;quot;&lt;br /&gt;
	]&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/templatedata&amp;gt;&lt;br /&gt;
== Examples ==&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight inline lang=&amp;quot;wikitext&amp;quot;&amp;gt;{{boolean|yes}}&amp;lt;/syntaxhighlight&amp;gt; -&amp;gt; {{boolean|yes}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight inline lang=&amp;quot;wikitext&amp;quot;&amp;gt;{{boolean|Yes}}&amp;lt;/syntaxhighlight&amp;gt; -&amp;gt; {{boolean|Yes}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight inline lang=&amp;quot;wikitext&amp;quot;&amp;gt;{{boolean|N}}&amp;lt;/syntaxhighlight&amp;gt; -&amp;gt; {{boolean|N}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight inline lang=&amp;quot;wikitext&amp;quot;&amp;gt;{{boolean||default=false}}&amp;lt;/syntaxhighlight&amp;gt; -&amp;gt; {{boolean||default=false}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight inline lang=&amp;quot;wikitext&amp;quot;&amp;gt;{{boolean||default=yes}}&amp;lt;/syntaxhighlight&amp;gt; -&amp;gt; {{boolean||default=yes}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight inline lang=&amp;quot;wikitext&amp;quot;&amp;gt;{{boolean|asdf|default-invalid=invalid}}&amp;lt;/syntaxhighlight&amp;gt; -&amp;gt; {{boolean|asdf|default-invalid=invalid}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/noinclude&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Boolean&amp;diff=90</id>
		<title>Template:Boolean</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Boolean&amp;diff=90"/>
		<updated>2025-03-02T07:42:53Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Created page with &amp;quot;&amp;lt;includeonly&amp;gt;{{#switch: {{lc: {{#if: {{{value|}}}|{{{value}}}|{{#if: {{{1|}}}|{{{1}}}|{{{default|false}}}}}}}}} |y|yes|true=true |n|no|false=false |{{#if: {{{default-invalid|false}}}|{{{boolean|{{{default-invalid|false}}}}}}||}} }}&amp;lt;/includeonly&amp;gt;&amp;lt;!--  --&amp;gt;&amp;lt;noinclude&amp;gt; &amp;lt;templatedata&amp;gt; { 	&amp;quot;params&amp;quot;: { 		&amp;quot;1&amp;quot;: { 			&amp;quot;aliases&amp;quot;: [ 				&amp;quot;value&amp;quot; 			], 			&amp;quot;label&amp;quot;: &amp;quot;Value&amp;quot;, 			&amp;quot;description&amp;quot;: &amp;quot;Value to turn into a boolean. \&amp;quot;y\&amp;quot;, \&amp;quot;yes\&amp;quot; or \&amp;quot;true\&amp;quot; will turn into \&amp;quot;true\&amp;quot;; \&amp;quot;n\&amp;quot;, \&amp;quot;no\&amp;quot;...&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;includeonly&amp;gt;{{#switch: {{lc: {{#if: {{{value|}}}|{{{value}}}|{{#if: {{{1|}}}|{{{1}}}|{{{default|false}}}}}}}}}&lt;br /&gt;
|y|yes|true=true&lt;br /&gt;
|n|no|false=false&lt;br /&gt;
|{{#if: {{{default-invalid|false}}}|{{{boolean|{{{default-invalid|false}}}}}}||}}&lt;br /&gt;
}}&amp;lt;/includeonly&amp;gt;&amp;lt;!--&lt;br /&gt;
&lt;br /&gt;
--&amp;gt;&amp;lt;noinclude&amp;gt;&lt;br /&gt;
&amp;lt;templatedata&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
	&amp;quot;params&amp;quot;: {&lt;br /&gt;
		&amp;quot;1&amp;quot;: {&lt;br /&gt;
			&amp;quot;aliases&amp;quot;: [&lt;br /&gt;
				&amp;quot;value&amp;quot;&lt;br /&gt;
			],&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Value&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Value to turn into a boolean. \&amp;quot;y\&amp;quot;, \&amp;quot;yes\&amp;quot; or \&amp;quot;true\&amp;quot; will turn into \&amp;quot;true\&amp;quot;; \&amp;quot;n\&amp;quot;, \&amp;quot;no\&amp;quot; or \&amp;quot;false\&amp;quot; will turn into \&amp;quot;false\&amp;quot;. Case insensitive.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;boolean&amp;quot;,&lt;br /&gt;
			&amp;quot;suggested&amp;quot;: true&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;default&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Default&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Default value to fall back to if the passed value is empty. Accepts the same values as the value parameter.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;boolean&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;false&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;default-invalid&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Default for invalid values&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Default value for invalid values. Accepts the same values as the \&amp;quot;values\&amp;quot; parameter, or an empty string.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;boolean&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;false&amp;quot;&lt;br /&gt;
		}&lt;br /&gt;
	},&lt;br /&gt;
	&amp;quot;description&amp;quot;: &amp;quot;Parse a boolean argument (\&amp;quot;y\&amp;quot;, \&amp;quot;yes\&amp;quot;, \&amp;quot;n\&amp;quot;, \&amp;quot;no\&amp;quot;, ...) and turn it into either \&amp;quot;true\&amp;quot; or \&amp;quot;false\&amp;quot;.&amp;quot;,&lt;br /&gt;
	&amp;quot;paramOrder&amp;quot;: [&lt;br /&gt;
		&amp;quot;1&amp;quot;,&lt;br /&gt;
		&amp;quot;default&amp;quot;,&lt;br /&gt;
		&amp;quot;default-invalid&amp;quot;&lt;br /&gt;
	]&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/templatedata&amp;gt;&lt;br /&gt;
== Examples ==&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight inline lang=&amp;quot;wikitext&amp;quot;&amp;gt;{{boolean|yes}}&amp;lt;/syntaxhighlight&amp;gt; -&amp;gt; {{boolean|yes}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight inline lang=&amp;quot;wikitext&amp;quot;&amp;gt;{{boolean|Yes}}&amp;lt;/syntaxhighlight&amp;gt; -&amp;gt; {{boolean|Yes}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight inline lang=&amp;quot;wikitext&amp;quot;&amp;gt;{{boolean|N}}&amp;lt;/syntaxhighlight&amp;gt; -&amp;gt; {{boolean|N}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight inline lang=&amp;quot;wikitext&amp;quot;&amp;gt;{{boolean||default=false}}&amp;lt;/syntaxhighlight&amp;gt; -&amp;gt; {{boolean||default=false}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight inline lang=&amp;quot;wikitext&amp;quot;&amp;gt;{{boolean||default=yes}}&amp;lt;/syntaxhighlight&amp;gt; -&amp;gt; {{boolean||default=yes}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight inline lang=&amp;quot;wikitext&amp;quot;&amp;gt;{{boolean|asdf|default-invalid=invalid}}&amp;lt;/syntaxhighlight&amp;gt; -&amp;gt; {{boolean|asdf|default-invalid=invalid}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/noinclude&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Getting_started&amp;diff=89</id>
		<title>User:Knuxify/Draft:Getting started</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Getting_started&amp;diff=89"/>
		<updated>2025-02-27T21:31:55Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Created page with &amp;quot;This page serves as an introduction to the basics of mainlining.  == Prerequisites ==  * A computer running Linux, which will handle building the kernel. ** If you&amp;#039;re on Windows, you can use WSL (though flashing the kernel to your device might be a bit challenging, TODO). ** (Note about recommended specs goes here; faster hardware is better, but only necessary bits are rebuilt on subsequent builds; also mention ccache?) * Some familiarity with the Linux shell and User:...&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;This page serves as an introduction to the basics of mainlining.&lt;br /&gt;
&lt;br /&gt;
== Prerequisites ==&lt;br /&gt;
&lt;br /&gt;
* A computer running Linux, which will handle building the kernel.&lt;br /&gt;
** If you&#039;re on Windows, you can use WSL (though flashing the kernel to your device might be a bit challenging, TODO).&lt;br /&gt;
** (Note about recommended specs goes here; faster hardware is better, but only necessary bits are rebuilt on subsequent builds; also mention ccache?)&lt;br /&gt;
* Some familiarity with the Linux shell and [[User:Knuxify/Draft:C crash course|C programming language syntax]] is recommended.&lt;br /&gt;
&lt;br /&gt;
== Getting to know your device and SoC ==&lt;br /&gt;
&lt;br /&gt;
{{todo|These are both topics worthy of their own page. Some things to mention here:&lt;br /&gt;
&lt;br /&gt;
* Finding out whether the SoC is supported to mainline and, if so, how well.&lt;br /&gt;
* Finding out what components your device has (it&#039;s nice to keep a table!)}}&lt;br /&gt;
&lt;br /&gt;
== Preparing the build environment ==&lt;br /&gt;
&lt;br /&gt;
In order to mainline a device, we need to be able to cross-compile the Linux kernel for it.&lt;br /&gt;
&lt;br /&gt;
=== Downloading the Linux kernel source code ===&lt;br /&gt;
&lt;br /&gt;
Depending on your SoC&#039;s support status:&lt;br /&gt;
&lt;br /&gt;
* There may be an up-to-date maintained [[close-to mainline]] fork of the Linux kernel for your device&#039;s SoC; if there is one, start from it.&lt;br /&gt;
* If there is no dedicated fork for your device&#039;s SoC, or the fork is out of date, start with either:&lt;br /&gt;
** &#039;&#039;&#039;The latest stable tag&#039;&#039;&#039; directly from Torvalds&#039; tree (see [https://web.git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/] or &amp;lt;code&amp;gt;github.com/torvalds/linux&amp;lt;/code&amp;gt;).&lt;br /&gt;
** For very new SoCs with ongoing work, you may want to use the &#039;&#039;&#039;linux-next tree&#039;&#039;&#039; instead.&lt;br /&gt;
&lt;br /&gt;
If you&#039;re on GitHub, you can fork [https://github.com/torvalds/linux the torvalds/linux repository] and start from there.&lt;br /&gt;
&lt;br /&gt;
Once you have your kernel cloned, switch to the latest tag, then create a new feature branch from it:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ git checkout v6.14  # replace 6.14 with latest kernel version&lt;br /&gt;
$ git checkout -b codename-mainline  # git checkout -b creates a new branch based on current HEAD and checks out into it&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
{{todo|Link to some nice guide on git here (and probably elsewhere in the page)}}&lt;br /&gt;
&lt;br /&gt;
=== Cross-compiler setup ===&lt;br /&gt;
&lt;br /&gt;
{{todo|Explain cross-compiler setup; where to get toolchains (AUR for Arch users? Linaro?), postmarketOS envkernel.sh}}&lt;br /&gt;
&lt;br /&gt;
=== Selecting/creating a defconfig ===&lt;br /&gt;
&lt;br /&gt;
The &#039;&#039;&#039;kernel config&#039;&#039;&#039; dictates which drivers and platform-specific support bits (including DTBs) get built. There are a handful of pre-made configs, called &#039;&#039;&#039;defconfigs&#039;&#039;&#039;, in &amp;lt;code&amp;gt;arch/{arm,arm64,...}/configs&amp;lt;/code&amp;gt; - use &amp;lt;code&amp;gt;make name_defconfig&amp;lt;/code&amp;gt; to build them.&lt;br /&gt;
&lt;br /&gt;
{{todo|Common ARM(64) config? Which options to select/unselect? pmbootstrap kconfig check might be useful here}}&lt;br /&gt;
&lt;br /&gt;
=== Adding a device tree for your device ===&lt;br /&gt;
&lt;br /&gt;
Devices using ARM chipsets use [[devicetree]]s to describe the hardware. See [[Devicetree/Writing a Linux device tree]] for a guide.&lt;br /&gt;
&lt;br /&gt;
=== Building the kernel ===&lt;br /&gt;
&lt;br /&gt;
{{todo|&amp;lt;code&amp;gt;make -j$(nproc)&amp;lt;/code&amp;gt;}}&lt;br /&gt;
&lt;br /&gt;
=== Packaging the kernel into a boot image ===&lt;br /&gt;
&lt;br /&gt;
{{todo|See how I do it in [https://github.com/refractionware/linux/blob/meta/tools/mainline-tools mainline-tools], mention pmbootstrap build --envkernel?}}&lt;br /&gt;
&lt;br /&gt;
Then, flash the resulting kernel to the device.&lt;br /&gt;
&lt;br /&gt;
== Getting the kernel to boot ==&lt;br /&gt;
&lt;br /&gt;
{{todo|UART, DTBO trickery}}&lt;br /&gt;
&lt;br /&gt;
== See also ==&lt;br /&gt;
&lt;br /&gt;
{{todo|pmOS wiki has links to talks and resources}}&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Category:To-do_items&amp;diff=88</id>
		<title>Category:To-do items</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Category:To-do_items&amp;diff=88"/>
		<updated>2025-02-27T21:00:13Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Created page with &amp;quot;Pages containing to-do items. All pages using the &amp;lt;code&amp;gt;todo&amp;lt;/code&amp;gt; template are automatically added here.&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;Pages containing to-do items. All pages using the [[Template:Todo|&amp;lt;code&amp;gt;todo&amp;lt;/code&amp;gt; template]] are automatically added here.&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Todo&amp;diff=87</id>
		<title>Template:Todo</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Todo&amp;diff=87"/>
		<updated>2025-02-27T20:58:59Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;!-- Dark-mode colors are defined in the template style --&amp;gt;&amp;lt;templatestyles src=&amp;quot;Todo/style.css&amp;quot;/&amp;gt;&amp;lt;!--&lt;br /&gt;
--&amp;gt;&amp;lt;includeonly&amp;gt;{{Icon box&lt;br /&gt;
| box-icons = [[File:Red warning icon.svg|20px|link=|TODO]]&lt;br /&gt;
| box-text = &amp;lt;b&amp;gt;TODO:&amp;lt;/b&amp;gt; {{{1}}}&lt;br /&gt;
| border-color = #b60000&lt;br /&gt;
| border-width = 1px&lt;br /&gt;
| background = #fdd1d1&lt;br /&gt;
| class = box-todo&lt;br /&gt;
}}&amp;lt;!--&lt;br /&gt;
Category:&lt;br /&gt;
--&amp;gt;{{#if: {{{nocategory|}}}||[[Category:To-do items]]}}&amp;lt;/includeonly&amp;gt;&amp;lt;!--&lt;br /&gt;
&lt;br /&gt;
--&amp;gt;&amp;lt;noinclude&amp;gt;&lt;br /&gt;
&amp;lt;templatedata&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
	&amp;quot;params&amp;quot;: {&lt;br /&gt;
		&amp;quot;1&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Text&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Text to place in the box&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;unbalanced-wikitext&amp;quot;,&lt;br /&gt;
			&amp;quot;required&amp;quot;: true&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;nocategory&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;No category&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;If true/yes, do not add this page to the \&amp;quot;To-do items\&amp;quot; category.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;boolean&amp;quot;&lt;br /&gt;
		}&lt;br /&gt;
	},&lt;br /&gt;
	&amp;quot;description&amp;quot;: &amp;quot;TODO box containing a to-do item. Also adds the page to the \&amp;quot;To-do items\&amp;quot; category; this behavior can be disabled with the \&amp;quot;nocategory\&amp;quot; parameter.&amp;quot;,&lt;br /&gt;
	&amp;quot;format&amp;quot;: &amp;quot;inline&amp;quot;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/templatedata&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Example ==&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;{{todo|This is &#039;&#039;&#039;yet to be done&#039;&#039;&#039;.}}&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
{{todo|This is &#039;&#039;&#039;yet to be done&#039;&#039;&#039;.|nocategory=yes}}&lt;br /&gt;
&amp;lt;/noinclude&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=File:Red_warning_icon.svg&amp;diff=86</id>
		<title>File:Red warning icon.svg</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=File:Red_warning_icon.svg&amp;diff=86"/>
		<updated>2025-02-27T20:57:11Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: == Licensing ==
{{MIT|1=2011-2019 [https://phabricator.wikimedia.org/diffusion/GOJU/browse/master/AUTHORS.txt OOjs UI Team and other contributors]}}&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Summary ==&lt;br /&gt;
== Licensing ==&lt;br /&gt;
{{MIT|1=2011-2019 [https://phabricator.wikimedia.org/diffusion/GOJU/browse/master/AUTHORS.txt OOjs UI Team and other contributors]}}&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Todo/style.css&amp;diff=85</id>
		<title>Template:Todo/style.css</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Todo/style.css&amp;diff=85"/>
		<updated>2025-02-27T20:55:17Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Created page with &amp;quot;html.skin-theme-clientpref-night .box-todo { 	color: #fff !important; 	background-color: #5c1e1e !important; 	border-color: #c64242 !important; }  @media (prefers-color-scheme: dark) { 	html.skin-theme-clientpref-os .box-todo { 		color: #fff !important; 		background-color: #5c1e1e !important; 		border-color: #c64242 !important; 	} }&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;html.skin-theme-clientpref-night .box-todo {&lt;br /&gt;
	color: #fff !important;&lt;br /&gt;
	background-color: #5c1e1e !important;&lt;br /&gt;
	border-color: #c64242 !important;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
@media (prefers-color-scheme: dark) {&lt;br /&gt;
	html.skin-theme-clientpref-os .box-todo {&lt;br /&gt;
		color: #fff !important;&lt;br /&gt;
		background-color: #5c1e1e !important;&lt;br /&gt;
		border-color: #c64242 !important;&lt;br /&gt;
	}&lt;br /&gt;
}&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Todo&amp;diff=84</id>
		<title>Template:Todo</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Todo&amp;diff=84"/>
		<updated>2025-02-27T20:54:12Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Created page with &amp;quot;&amp;lt;!-- Dark-mode colors are defined in the template style --&amp;gt;&amp;lt;templatestyles src=&amp;quot;Todo/style.css&amp;quot;/&amp;gt;&amp;lt;!-- --&amp;gt;&amp;lt;includeonly&amp;gt;{{Icon box | box-icons = TODO | box-text = &amp;lt;b&amp;gt;TODO:&amp;lt;/b&amp;gt; {{{1}}} | border-color = #b60000 | border-width = 1px | background = #fdd1d1 | class = box-todo }}&amp;lt;!-- Category: --&amp;gt;{{#if: {{{nocategory|}}}||Category:Todo Items}}&amp;lt;/includeonly&amp;gt;&amp;lt;!--  --&amp;gt;&amp;lt;noinclude&amp;gt; &amp;lt;templatedata&amp;gt; { 	&amp;quot;params&amp;quot;: { 		&amp;quot;1&amp;quot;: { 			&amp;quot;label&amp;quot;: &amp;quot;Text&amp;quot;,...&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;!-- Dark-mode colors are defined in the template style --&amp;gt;&amp;lt;templatestyles src=&amp;quot;Todo/style.css&amp;quot;/&amp;gt;&amp;lt;!--&lt;br /&gt;
--&amp;gt;&amp;lt;includeonly&amp;gt;{{Icon box&lt;br /&gt;
| box-icons = [[File:Red warning icon.svg|20px|link=|TODO]]&lt;br /&gt;
| box-text = &amp;lt;b&amp;gt;TODO:&amp;lt;/b&amp;gt; {{{1}}}&lt;br /&gt;
| border-color = #b60000&lt;br /&gt;
| border-width = 1px&lt;br /&gt;
| background = #fdd1d1&lt;br /&gt;
| class = box-todo&lt;br /&gt;
}}&amp;lt;!--&lt;br /&gt;
Category:&lt;br /&gt;
--&amp;gt;{{#if: {{{nocategory|}}}||[[Category:Todo Items]]}}&amp;lt;/includeonly&amp;gt;&amp;lt;!--&lt;br /&gt;
&lt;br /&gt;
--&amp;gt;&amp;lt;noinclude&amp;gt;&lt;br /&gt;
&amp;lt;templatedata&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
	&amp;quot;params&amp;quot;: {&lt;br /&gt;
		&amp;quot;1&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Text&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Text to place in the box&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;unbalanced-wikitext&amp;quot;,&lt;br /&gt;
			&amp;quot;required&amp;quot;: true&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;nocategory&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;No category&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;If true/yes, do not add this page to the \&amp;quot;To-do items\&amp;quot; category.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;boolean&amp;quot;&lt;br /&gt;
		}&lt;br /&gt;
	},&lt;br /&gt;
	&amp;quot;description&amp;quot;: &amp;quot;TODO box containing a to-do item. Also adds the page to the \&amp;quot;To-do items\&amp;quot; category; this behavior can be disabled with the \&amp;quot;nocategory\&amp;quot; parameter.&amp;quot;,&lt;br /&gt;
	&amp;quot;format&amp;quot;: &amp;quot;inline&amp;quot;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/templatedata&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Example ==&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;{{todo|This is &#039;&#039;&#039;yet to be done&#039;&#039;&#039;.}}&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
{{todo|This is &#039;&#039;&#039;yet to be done&#039;&#039;&#039;.|nocategory=yes}}&lt;br /&gt;
&amp;lt;/noinclude&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Devicetree_take_2&amp;diff=83</id>
		<title>User:Knuxify/Draft:Devicetree take 2</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Devicetree_take_2&amp;diff=83"/>
		<updated>2025-02-27T20:42:15Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Blanked the page&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Devicetree/Bindings&amp;diff=82</id>
		<title>Devicetree/Bindings</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Devicetree/Bindings&amp;diff=82"/>
		<updated>2025-02-22T07:38:11Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Navbox devicetree}}&lt;br /&gt;
Devicetrees are validated using &#039;&#039;&#039;devicetree schema&#039;&#039;&#039;; this schema specifies allowed properties for nodes based on their &amp;lt;code&amp;gt;compatible&amp;lt;/code&amp;gt; string. Devicetree schema is defined through &#039;&#039;&#039;bindings&#039;&#039;&#039;, YAML files containing schema information (older bindings use TXT format, but this is deprecated).&lt;br /&gt;
&lt;br /&gt;
Bindings for most Linux components can be found in &amp;lt;code&amp;gt;Documentation/devicetree/bindings&amp;lt;/code&amp;gt;; there is also a [https://github.com/devicetree-org/dt-schema core DT schema] defining the most basic components and syntax.&lt;br /&gt;
&lt;br /&gt;
== Validating DT bindings ==&lt;br /&gt;
&lt;br /&gt;
The Linux kernel has tools for validating devicetree schema bindings. Getting the DT binding check to pass is required for upstreaming the binding.&lt;br /&gt;
&lt;br /&gt;
To verify all DT bindings, run:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make dt_binding_check&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
You can also verify only a specific binding by providing its filename in the &amp;lt;code&amp;gt;DT_SCHEMA_FILES&amp;lt;/code&amp;gt; option. This option takes either a filename or a directory name:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make dt_binding_check DT_SCHEMA_FILES=brcm,bcm590xx.yaml  # Checks all bindings named brcm,bcm590xx.yaml&lt;br /&gt;
$ make dt_binding_check DT_SCHEMA_FILES=qcom    # Checks all bindings in any (sub)folder named &amp;quot;qcom&amp;quot;&lt;br /&gt;
$ make dt_binding_check DT_SCHEMA_FILES=/gpio/  # Checks all bindings in /gpio folder&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
To verify a DTS file against a DT schema, build the DTB target directly and provide the &amp;lt;code&amp;gt;CHECK_DTBS=y&amp;lt;/code&amp;gt; option alongside &amp;lt;code&amp;gt;DT_SCHEMA_FILES&amp;lt;/code&amp;gt;:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make CHECK_DTBS=y DT_SCHEMA_FILES=trivial-devices.yaml qcom/sm8450-hdk.dtb&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== See also ==&lt;br /&gt;
&lt;br /&gt;
* From Linux kernel documentation:&lt;br /&gt;
** [https://docs.kernel.org/devicetree/bindings/writing-schema.html Writing Devicetree Bindings in json-schema]&lt;br /&gt;
** [https://docs.kernel.org/devicetree/bindings/writing-bindings.html DOs and DON’Ts for designing and writing Devicetree bindings]&lt;br /&gt;
** [https://docs.kernel.org/devicetree/bindings/submitting-patches.html Submitting Devicetree (DT) binding patches]&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Devicetree/DTS_syntax&amp;diff=81</id>
		<title>Devicetree/DTS syntax</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Devicetree/DTS_syntax&amp;diff=81"/>
		<updated>2025-02-20T18:20:34Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: /* TODOs */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Navbox devicetree}}&lt;br /&gt;
&lt;br /&gt;
This page serves as a guide to the device tree source (DTS) file syntax.&lt;br /&gt;
&lt;br /&gt;
== TODOs ==&lt;br /&gt;
&lt;br /&gt;
* Quick intro to explain how things are typically laid out in ARM chips, buses like I2C, etc. - how &amp;lt;code&amp;gt;reg&amp;lt;/code&amp;gt; addresses work, how DTS syntax describes this layout&lt;br /&gt;
* Split up into more granular subsections&lt;br /&gt;
&lt;br /&gt;
== Basic DTS syntax ==&lt;br /&gt;
&lt;br /&gt;
Here is a very simple DTS file to explain the basics of what you might see in a device tree source file:&lt;br /&gt;
&lt;br /&gt;
{{SyntaxHighlight header|foo.dts}}&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	&lt;br /&gt;
	my_node: node1@1000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foo&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x1000 0x54&amp;gt;;&lt;br /&gt;
		vendor,bar-factor = &amp;lt;0x2a&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
&lt;br /&gt;
	node2@2000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,bar&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x2000 0xa4&amp;gt;;&lt;br /&gt;
		vendor,baz-companion = &amp;lt;&amp;amp;my_node&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
&lt;br /&gt;
	i2c-controller@3000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x3000 0x800&amp;gt;;&lt;br /&gt;
		&lt;br /&gt;
		#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
		#size-cells = &amp;lt;0&amp;gt;;&lt;br /&gt;
		&lt;br /&gt;
		sensor@10 {&lt;br /&gt;
			compatible = &amp;quot;vendor,baz-sensor&amp;quot;;&lt;br /&gt;
			reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
		};&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
In this example, we define an empty DTS; in its root node (&amp;lt;code&amp;gt;/&amp;lt;/code&amp;gt;), we place three nodes: a node named &amp;quot;node1&amp;quot; with a label &amp;quot;my_node&amp;quot; at address 0x1000, a node named &amp;quot;node2&amp;quot; at address 0x2000, and a node named &amp;quot;i2c-controller&amp;quot; at address 0x3000.&lt;br /&gt;
&lt;br /&gt;
A node contains:&lt;br /&gt;
* A &amp;lt;code&amp;gt;compatible&amp;lt;/code&amp;gt; value (here &amp;lt;code&amp;gt;&amp;quot;vendor,foo&amp;quot;&amp;lt;/code&amp;gt;). This specifies what kind of component it is; Linux uses this information to load the correct driver.&lt;br /&gt;
* A &amp;lt;code&amp;gt;reg&amp;lt;/code&amp;gt; value. In this case, the first parameter is the base address in memory (&amp;lt;code&amp;gt;0x1000&amp;lt;/code&amp;gt;), and the second is the size it occupies (&amp;lt;code&amp;gt;0x54&amp;lt;/code&amp;gt;). The amount of cells for the address and size are specified by the &amp;lt;code&amp;gt;#address-cells&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;#size-cells&amp;lt;/code&amp;gt; properties of the root node, respectively.&lt;br /&gt;
** You might notice that the i2c-controller node defines another set of these &amp;lt;code&amp;gt;#address-cells&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;#size-cells&amp;lt;/code&amp;gt; properties - this is because I2C devices contain their own subdevices with addresses ranging from 0x08 to 0x7f (todo verify), and they do not use a size.&lt;br /&gt;
* A custom vendor-specific property, &amp;lt;code&amp;gt;vendor,bar-factor&amp;lt;/code&amp;gt;, which takes a number.&lt;br /&gt;
&lt;br /&gt;
On node 2 there is also a property, &amp;lt;code&amp;gt;vendor,baz-companion&amp;lt;/code&amp;gt;, which takes a pointer to another node - here the one we labeled &amp;quot;my_node&amp;quot;.&lt;br /&gt;
&lt;br /&gt;
== Working with included DTSIs ==&lt;br /&gt;
&lt;br /&gt;
Very often you&#039;ll see &amp;lt;code&amp;gt;#include&amp;lt;/code&amp;gt; directives; these can either include header files (which usually contain constants defined with &amp;lt;code&amp;gt;#define&amp;lt;/code&amp;gt;, similarly to C) or other DTSes. DTS files meant for inclusion are called &#039;&#039;&#039;DTS includes&#039;&#039;&#039; and use the &#039;&#039;&#039;.dtsi&#039;&#039;&#039; file extension. &lt;br /&gt;
&lt;br /&gt;
Usually, an SoC will have a common DTS include with all of the relevant nodes for that SoC. A board&#039;s DTS will then include the SoC DTSI.&lt;br /&gt;
&lt;br /&gt;
As an example, here&#039;s a very bare-bones DTSI for a fictional &amp;quot;FOO1234&amp;quot; SoC:&lt;br /&gt;
&lt;br /&gt;
{{SyntaxHighlight header|foo1234.dtsi}}&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/*&lt;br /&gt;
 * Common DTSI for Foobar FOO1234 System-on-a-Chip.&lt;br /&gt;
 */&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
    cpus {&lt;br /&gt;
		#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
		#size-cells = &amp;lt;0&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
		cpu0: cpu@0 {&lt;br /&gt;
			device_type = &amp;quot;cpu&amp;quot;;&lt;br /&gt;
			compatible = &amp;quot;arm,cortex-a7&amp;quot;;&lt;br /&gt;
			reg = &amp;lt;0&amp;gt;;&lt;br /&gt;
			clock-frequency = &amp;lt;1000000000&amp;gt;;&lt;br /&gt;
		};&lt;br /&gt;
    };&lt;br /&gt;
&lt;br /&gt;
    soc {&lt;br /&gt;
        /* ... */&lt;br /&gt;
&lt;br /&gt;
        i2c1: i2c@3000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x3000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        i2c2: i2c@4000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x4000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        i2c3: i2c@5000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x5000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        /* ... */&lt;br /&gt;
    };&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Here is a DTS for a fictional device named &amp;quot;Quox Haystack&amp;quot; that uses the FOO1234 SoC:&lt;br /&gt;
&lt;br /&gt;
{{SyntaxHighlight header|foo1234-quox-haystack.dts}}&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/*&lt;br /&gt;
 * Device tree source for Quox Haystack based on FOO1234 SoC&lt;br /&gt;
 */&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
#include &amp;quot;foo1234.dtsi&amp;quot;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	compatible = &amp;quot;quox,haystack&amp;quot;, &amp;quot;foobar,foo1234&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
	memory@80000000 {&lt;br /&gt;
		device_type = &amp;quot;memory&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x80000000 0x40000000&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
&amp;amp;i2c1 {&lt;br /&gt;
    clock-frequency = &amp;lt;400000&amp;gt;;&lt;br /&gt;
    status = &amp;quot;okay&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
    sensor@10 {&lt;br /&gt;
		compatible = &amp;quot;foobar,baz-sensor&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Some interesting things to look out for:&lt;br /&gt;
&lt;br /&gt;
* The board DTS includes the SoC DTSI with a &amp;lt;code&amp;gt;#include &amp;quot;foo1234.dtsi&amp;quot;&amp;lt;/code&amp;gt; directive.&lt;br /&gt;
* We re-define the root &amp;lt;code&amp;gt;/&amp;lt;/code&amp;gt; node, and inside of it we place a &amp;lt;code&amp;gt;memory&amp;lt;/code&amp;gt; node. This node, as well as the &amp;lt;code&amp;gt;compatible&amp;lt;/code&amp;gt;, will be merged into the root node of the included DTSI.&lt;br /&gt;
* Outside of the root node, there is a node with a name starting with an ampersand (&amp;lt;code&amp;gt;&amp;amp;i2c1&amp;lt;/code&amp;gt;); this signifies a pointer to a labeled node (see node labels in the previous example). Like with the root node above, the contents of this node will be merged with the contents of the node with this label in the SoC DTSI.&lt;br /&gt;
** A similar effect could be achieved by overriding the &amp;lt;code&amp;gt;i2c1&amp;lt;/code&amp;gt; node under the root node, where it&#039;s located in the SoC DTSI (though the preferred way is to do it with a label - we do it here for demonstration purposes):&lt;br /&gt;
*: {{SyntaxHighlight header|foo1234-quox-haystack.dts}}&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line start=&amp;quot;3&amp;quot;&amp;gt;&lt;br /&gt;
/ {&lt;br /&gt;
	compatible = &amp;quot;quox,haystack&amp;quot;, &amp;quot;foobar,foo1234&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
    /* ... */&lt;br /&gt;
&lt;br /&gt;
	i2c1: i2c@3000 {&lt;br /&gt;
        clock-frequency = &amp;lt;400000&amp;gt;;&lt;br /&gt;
        status = &amp;quot;okay&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
        sensor@10 {&lt;br /&gt;
	    	compatible = &amp;quot;foobar,baz-sensor&amp;quot;;&lt;br /&gt;
	    	reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
	    };&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
For a more visual example - the merged version of these two files would look something like this:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
    compatible = &amp;quot;quox,haystack&amp;quot;, &amp;quot;foobar,foo1234&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
	memory@80000000 {&lt;br /&gt;
		device_type = &amp;quot;memory&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x80000000 0x40000000&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
	&lt;br /&gt;
    cpus {&lt;br /&gt;
		#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
		#size-cells = &amp;lt;0&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
		cpu0: cpu@0 {&lt;br /&gt;
			device_type = &amp;quot;cpu&amp;quot;;&lt;br /&gt;
			compatible = &amp;quot;arm,cortex-a7&amp;quot;;&lt;br /&gt;
			reg = &amp;lt;0&amp;gt;;&lt;br /&gt;
			clock-frequency = &amp;lt;1000000000&amp;gt;;&lt;br /&gt;
		};&lt;br /&gt;
    };&lt;br /&gt;
&lt;br /&gt;
    soc {&lt;br /&gt;
        /* ... */&lt;br /&gt;
&lt;br /&gt;
        i2c1: i2c@3000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x3000 0x800&amp;gt;;&lt;br /&gt;
            clock-frequency = &amp;lt;400000&amp;gt;;&lt;br /&gt;
            status = &amp;quot;okay&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
            sensor@10 {&lt;br /&gt;
                compatible = &amp;quot;foobar,baz-sensor&amp;quot;;&lt;br /&gt;
                reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
            };&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        i2c2: i2c@4000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x4000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        i2c3: i2c@5000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x5000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        /* ... */&lt;br /&gt;
    };&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Note/style.css&amp;diff=80</id>
		<title>Template:Note/style.css</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Note/style.css&amp;diff=80"/>
		<updated>2025-02-20T18:18:48Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;html.skin-theme-clientpref-night .box-note {&lt;br /&gt;
	color: #fff !important;&lt;br /&gt;
	background-color: #261c09 !important;&lt;br /&gt;
	border-color: #6a481c !important;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
@media (prefers-color-scheme: dark) {&lt;br /&gt;
	html.skin-theme-clientpref-os .box-note {&lt;br /&gt;
		color: #fff !important;&lt;br /&gt;
		background-color: #261c09 !important;&lt;br /&gt;
		border-color: #6a481c !important;&lt;br /&gt;
	}&lt;br /&gt;
}&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Icon_box&amp;diff=79</id>
		<title>Template:Icon box</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Icon_box&amp;diff=79"/>
		<updated>2025-02-20T18:16:47Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: add class property&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;includeonly&amp;gt;&amp;lt;table role=&amp;quot;{{{role|text container}}}&amp;quot; {{#if: {{{class|}}}|class=&amp;quot;{{{class}}}&amp;quot; }} style=&amp;quot;color: {{{color|inherit}}}; background-color: {{{background|inherit}}}; border: {{{border-width|1px}}} {{{border-style|solid}}} {{{border-color|#eaecf0}}}; margin: 4px {{#if: {{{margin|}}}|10%|0}}; border-collapse: collapse;&amp;quot;&amp;gt;&amp;lt;tr&amp;gt;&lt;br /&gt;
&amp;lt;td style=&amp;quot;padding: 2px 0 2px 0.9em; text-align: center; line-height: 1;&amp;quot;&amp;gt;&amp;lt;span style=&amp;quot;white-space: nowrap;&amp;quot;&amp;gt;{{{box-icons}}}&amp;lt;/span&amp;gt;&amp;lt;/td&amp;gt;&lt;br /&gt;
&amp;lt;td style=&amp;quot;padding: {{{padding|0.35em}}} 0.9em; width: 100%;&amp;quot;&amp;gt;{{{box-text}}}&amp;lt;/td&amp;gt;&lt;br /&gt;
&amp;lt;/tr&amp;gt;&amp;lt;/table&amp;gt;&amp;lt;/includeonly&amp;gt;&amp;lt;!--&lt;br /&gt;
&lt;br /&gt;
--&amp;gt;&amp;lt;noinclude&amp;gt;&lt;br /&gt;
&amp;lt;templatedata&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
	&amp;quot;params&amp;quot;: {&lt;br /&gt;
		&amp;quot;role&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;HTML role&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;HTML accessible role parameter to add to the box.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;text container&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;color&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Text color&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Text color in any format supported by CSS (hex, rgb(...), ...)&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;inherit&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;background&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Background color&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Background color in any format supported by CSS (hex, rgb(...), ...)&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;inherit&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;border-width&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Border width&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Border width with unit&amp;quot;,&lt;br /&gt;
			&amp;quot;example&amp;quot;: &amp;quot;1px&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;1px&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;border-style&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Border style&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;CSS border-style value&amp;quot;,&lt;br /&gt;
			&amp;quot;example&amp;quot;: &amp;quot;solid&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;solid&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;border-color&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Border color&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Text color in any format supported by CSS (hex, rgb(...), ...)&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;#eaecf0&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;box-icons&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Box icons&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Standard wikitext containing the icons to place inside of the box, see example syntax.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;content&amp;quot;,&lt;br /&gt;
			&amp;quot;suggested&amp;quot;: true&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;padding&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Padding&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Padding to add to the box, with the unit&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;0.35em&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;box-text&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Box text&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Text inside of the box.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;content&amp;quot;,&lt;br /&gt;
			&amp;quot;required&amp;quot;: true&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;margin&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Enable margin&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;If set, adds a margin from the sides of the box.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;boolean&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;false&amp;quot;,&lt;br /&gt;
			&amp;quot;suggested&amp;quot;: true&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;class&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;HTML class&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;HTML class/classes to add to the box, space-separated.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;&lt;br /&gt;
		}&lt;br /&gt;
	},&lt;br /&gt;
	&amp;quot;description&amp;quot;: &amp;quot;Floating box with an icon and background. Used for licensing templates, Template:Note and similar boxes.&amp;quot;,&lt;br /&gt;
	&amp;quot;format&amp;quot;: &amp;quot;block&amp;quot;,&lt;br /&gt;
	&amp;quot;paramOrder&amp;quot;: [&lt;br /&gt;
		&amp;quot;box-text&amp;quot;,&lt;br /&gt;
		&amp;quot;box-icons&amp;quot;,&lt;br /&gt;
		&amp;quot;margin&amp;quot;,&lt;br /&gt;
		&amp;quot;color&amp;quot;,&lt;br /&gt;
		&amp;quot;background&amp;quot;,&lt;br /&gt;
		&amp;quot;border-color&amp;quot;,&lt;br /&gt;
		&amp;quot;border-style&amp;quot;,&lt;br /&gt;
		&amp;quot;border-width&amp;quot;,&lt;br /&gt;
		&amp;quot;padding&amp;quot;,&lt;br /&gt;
		&amp;quot;role&amp;quot;,&lt;br /&gt;
		&amp;quot;class&amp;quot;&lt;br /&gt;
	]&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/templatedata&amp;gt;&lt;br /&gt;
&amp;lt;/noinclude&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Devicetree&amp;diff=78</id>
		<title>Devicetree</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Devicetree&amp;diff=78"/>
		<updated>2025-02-20T18:10:40Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: /* Introduction */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Navbox devicetree}}&lt;br /&gt;
The &#039;&#039;&#039;devicetree&#039;&#039;&#039; (device tree, DT) is a tree structure that describes the hardware register layout and configuration of a device. In the Linux kernel, as well as in other DT-using projects like U-Boot, it is the primary method of discovering peripherals on embedded platforms such as ARM.&lt;br /&gt;
&lt;br /&gt;
Devicetrees are written in a plaintext format known as the &#039;&#039;&#039;Device Tree Source (DTS)&#039;&#039;&#039; format. The DTS is later compiled into a &#039;&#039;&#039;Device Tree Blob (DTB)&#039;&#039;&#039;; in this form, it can be loaded by software/firmware.&lt;br /&gt;
&lt;br /&gt;
Devicetrees are validated using &#039;&#039;&#039;devicetree schema&#039;&#039;&#039;, which is described in &#039;&#039;&#039;DT bindings&#039;&#039;&#039;; see [[/Bindings]] for more information.&lt;br /&gt;
&lt;br /&gt;
== Introduction ==&lt;br /&gt;
&lt;br /&gt;
An SoC (System-on-Chip) comprises of many subcomponents: timer, clock controller, I2C/SPI controller, GPIO, interrupt controller, SDHCI storage, USB, and so on. Each needs its own driver, and for most parts the exact implementation differs between chip manufacturers. Most of them expose a static range of addresses in MMIO (memory-mapped IO) space that the system can use to communicate with them. &lt;br /&gt;
&lt;br /&gt;
Additionally, there may be other peripherals connected to the system - often through a bus like I2C or SPI, or as a simple device controlled by a GPIO.&lt;br /&gt;
&lt;br /&gt;
On a standard x86 system, peripherals are usually autodetected, either through ACPI, or by being on a bus like PCI or USB. On most embedded platforms like ARM, however,  there is no such autodetection method, and the hardware needs to be described manually.&lt;br /&gt;
&lt;br /&gt;
The solution for this, used by both the Linux kernel, as well as a variety of other projects like U-Boot, is the &#039;&#039;&#039;devicetree&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
The following is a very simple example DTS (device tree source):&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
	my_node: node1@1000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foo&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x1000 0x54&amp;gt;;&lt;br /&gt;
		vendor,bar-factor = &amp;lt;0x2a&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
&lt;br /&gt;
	i2c-controller@3000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x3000 0x800&amp;gt;;&lt;br /&gt;
		&lt;br /&gt;
		#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
		#size-cells = &amp;lt;0&amp;gt;;&lt;br /&gt;
		&lt;br /&gt;
		sensor@10 {&lt;br /&gt;
			compatible = &amp;quot;vendor,baz-sensor&amp;quot;;&lt;br /&gt;
			reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
		};&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
{{note|For a full guide to DTS syntax, see [[/DTS syntax]].}}&lt;br /&gt;
&lt;br /&gt;
The devicetree acts like a map of the hardware; it describes where each component is in register space, and stores configuration values for them. It also describes components located on buses like I2C and SPI, and can carry some metadata about the board/device (like the RAM size/base address, model code or chassis type).&lt;br /&gt;
&lt;br /&gt;
Devicetrees are written in the &#039;&#039;&#039;DTS&#039;&#039;&#039; (Device Tree Source) format; the source file can then be compiled into a &#039;&#039;&#039;DTB&#039;&#039;&#039; (Device Tree Blob), which software can parse to get all the necessary information about a given platform.&lt;br /&gt;
&lt;br /&gt;
On modern systems, the bootloader loads the DTB into a set place in memory; the Linux kernel then decodes the information from the DTB and initializes all the components based on it. (On 32-bit ARM, which predates widespread adoption of DTBs and DTB-capable bootloaders, an alternative mechanism exists in Linux to load a DTB appended to the kernel image).&lt;br /&gt;
&lt;br /&gt;
== History ==&lt;br /&gt;
&lt;br /&gt;
The initial version of the devicetree standard was developed as part of the OpenFirmware initiative; from this standard, the Flattened Device Tree (FDT) emerged and was adopted by the Linux kernel for PowerPC platforms. Around 2009, discussions began to include FDT support for ARM[1]. It was eventually added and first device trees began to appear in 2011[2], although the format didn&#039;t see wider usage (especially in vendor kernels) until around 2013/2014.&lt;br /&gt;
&lt;br /&gt;
Nowadays, the devicetree standard is managed by [https://www.devicetree.org/ devicetree.org]; they maintain the latest version of the [https://www.devicetree.org/specifications Devicetree Specification] and the related set of [https://github.com/devicetree-org/dt-schema core DT schema].&lt;br /&gt;
&lt;br /&gt;
Before the introduction of devicetrees, ARM kernels used &#039;&#039;&#039;board files&#039;&#039;&#039;. These were C files stored in &amp;lt;code&amp;gt;arch/arm/mach-*&amp;lt;/code&amp;gt; which served a similar purpose to devicetrees - they contained structures for defining component configuration (&amp;quot;platform data&amp;quot;). Unlike device trees however, they could also define C functions, since they were regular C sources compiled into the kernel. Board files technically still exist (citation needed?), but are no longer in wide use.&lt;br /&gt;
&lt;br /&gt;
== Devicetree sources in the Linux kernel ==&lt;br /&gt;
&lt;br /&gt;
TODO&lt;br /&gt;
&lt;br /&gt;
== Verifying DTS files ==&lt;br /&gt;
&lt;br /&gt;
The Linux kernel has tools for making sure that device tree sources (DTS) use the bindings correctly. These are useful when writing device sources; getting &lt;br /&gt;
the DT checks to pass is also mandatory for upstream inclusion of a DTS.&lt;br /&gt;
&lt;br /&gt;
To verify all DTS files built with the selected defconfig options, run:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make dtbs_check&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
To verify a specific DTS, build the DTB target directly and provide the &amp;lt;code&amp;gt;CHECK_DTBS=y&amp;lt;/code&amp;gt; option:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make CHECK_DTBS=y qcom/sm8450-hdk.dtb&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
You can also test a DTS against a specific subset of bindings by providing the &amp;lt;code&amp;gt;DT_SCHEMA_FILES&amp;lt;/code&amp;gt; variable as mentioned in the previous section:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make CHECK_DTBS=y DT_SCHEMA_FILES=trivial-devices.yaml qcom/sm8450-hdk.dtb&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Working with DTC ==&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;dtc&amp;lt;/code&amp;gt; tool handles compiling DTS files into DTBs, as well as decompiling DTBs back into DTS. (TODO: add instructions)&lt;br /&gt;
&lt;br /&gt;
== See also ==&lt;br /&gt;
&lt;br /&gt;
* From Linux kernel documentation:&lt;br /&gt;
** [https://docs.kernel.org/devicetree/bindings/dts-coding-style.html Devicetree Sources (DTS) Coding Style]&lt;br /&gt;
* On elinux.org:&lt;br /&gt;
** [https://elinux.org/Device_Tree_Reference Device Tree Reference]&lt;br /&gt;
** [https://elinux.org/Device_Tree_Reference Device Tree Usage]&lt;br /&gt;
&lt;br /&gt;
== References ==&lt;br /&gt;
&lt;br /&gt;
todo enable refs extension&lt;br /&gt;
&lt;br /&gt;
[1] https://www.mail-archive.com/linux-embedded@vger.kernel.org/msg01721.html&lt;br /&gt;
[2] https://github.com/torvalds/linux/commit/b85a3ef4ac65169b65fd2fe9bec7912bbf475ba4&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Devicetree&amp;diff=77</id>
		<title>Devicetree</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Devicetree&amp;diff=77"/>
		<updated>2025-02-20T18:10:14Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: /* Introduction */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Navbox devicetree}}&lt;br /&gt;
The &#039;&#039;&#039;devicetree&#039;&#039;&#039; (device tree, DT) is a tree structure that describes the hardware register layout and configuration of a device. In the Linux kernel, as well as in other DT-using projects like U-Boot, it is the primary method of discovering peripherals on embedded platforms such as ARM.&lt;br /&gt;
&lt;br /&gt;
Devicetrees are written in a plaintext format known as the &#039;&#039;&#039;Device Tree Source (DTS)&#039;&#039;&#039; format. The DTS is later compiled into a &#039;&#039;&#039;Device Tree Blob (DTB)&#039;&#039;&#039;; in this form, it can be loaded by software/firmware.&lt;br /&gt;
&lt;br /&gt;
Devicetrees are validated using &#039;&#039;&#039;devicetree schema&#039;&#039;&#039;, which is described in &#039;&#039;&#039;DT bindings&#039;&#039;&#039;; see [[/Bindings]] for more information.&lt;br /&gt;
&lt;br /&gt;
== Introduction ==&lt;br /&gt;
&lt;br /&gt;
An SoC (System-on-Chip) comprises of many subcomponents: timer, clock controller, I2C/SPI controller, GPIO, interrupt controller, SDHCI storage, USB, and so on. Each needs its own driver, and for most parts the exact implementation differs between chip manufacturers. Most of them expose a static range of addresses in MMIO (memory-mapped IO) space that the system can use to communicate with them. &lt;br /&gt;
&lt;br /&gt;
Additionally, there may be other peripherals connected to the system - often through a bus like I2C or SPI, or as a simple device controlled by a GPIO.&lt;br /&gt;
&lt;br /&gt;
On a standard x86 system, peripherals are usually autodetected, either through ACPI, or by being on a bus like PCI or USB. On most embedded platforms like ARM, however,  there is no such autodetection method, and the hardware needs to be described manually.&lt;br /&gt;
&lt;br /&gt;
The solution for this, used by both the Linux kernel, as well as a variety of other projects like U-Boot, is the &#039;&#039;&#039;devicetree&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
The following is a very simple example DTS (device tree source):&lt;br /&gt;
&lt;br /&gt;
{{note|For a full guide to DTS syntax, see [[/DTS syntax]].}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
	my_node: node1@1000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foo&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x1000 0x54&amp;gt;;&lt;br /&gt;
		vendor,bar-factor = &amp;lt;0x2a&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
&lt;br /&gt;
	i2c-controller@3000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x3000 0x800&amp;gt;;&lt;br /&gt;
		&lt;br /&gt;
		#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
		#size-cells = &amp;lt;0&amp;gt;;&lt;br /&gt;
		&lt;br /&gt;
		sensor@10 {&lt;br /&gt;
			compatible = &amp;quot;vendor,baz-sensor&amp;quot;;&lt;br /&gt;
			reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
		};&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The devicetree acts like a map of the hardware; it describes where each component is in register space, and stores configuration values for them. It also describes components located on buses like I2C and SPI, and can carry some metadata about the board/device (like the RAM size/base address, model code or chassis type).&lt;br /&gt;
&lt;br /&gt;
Devicetrees are written in the &#039;&#039;&#039;DTS&#039;&#039;&#039; (Device Tree Source) format; the source file can then be compiled into a &#039;&#039;&#039;DTB&#039;&#039;&#039; (Device Tree Blob), which software can parse to get all the necessary information about a given platform.&lt;br /&gt;
&lt;br /&gt;
On modern systems, the bootloader loads the DTB into a set place in memory; the Linux kernel then decodes the information from the DTB and initializes all the components based on it. (On 32-bit ARM, which predates widespread adoption of DTBs and DTB-capable bootloaders, an alternative mechanism exists in Linux to load a DTB appended to the kernel image).&lt;br /&gt;
&lt;br /&gt;
== History ==&lt;br /&gt;
&lt;br /&gt;
The initial version of the devicetree standard was developed as part of the OpenFirmware initiative; from this standard, the Flattened Device Tree (FDT) emerged and was adopted by the Linux kernel for PowerPC platforms. Around 2009, discussions began to include FDT support for ARM[1]. It was eventually added and first device trees began to appear in 2011[2], although the format didn&#039;t see wider usage (especially in vendor kernels) until around 2013/2014.&lt;br /&gt;
&lt;br /&gt;
Nowadays, the devicetree standard is managed by [https://www.devicetree.org/ devicetree.org]; they maintain the latest version of the [https://www.devicetree.org/specifications Devicetree Specification] and the related set of [https://github.com/devicetree-org/dt-schema core DT schema].&lt;br /&gt;
&lt;br /&gt;
Before the introduction of devicetrees, ARM kernels used &#039;&#039;&#039;board files&#039;&#039;&#039;. These were C files stored in &amp;lt;code&amp;gt;arch/arm/mach-*&amp;lt;/code&amp;gt; which served a similar purpose to devicetrees - they contained structures for defining component configuration (&amp;quot;platform data&amp;quot;). Unlike device trees however, they could also define C functions, since they were regular C sources compiled into the kernel. Board files technically still exist (citation needed?), but are no longer in wide use.&lt;br /&gt;
&lt;br /&gt;
== Devicetree sources in the Linux kernel ==&lt;br /&gt;
&lt;br /&gt;
TODO&lt;br /&gt;
&lt;br /&gt;
== Verifying DTS files ==&lt;br /&gt;
&lt;br /&gt;
The Linux kernel has tools for making sure that device tree sources (DTS) use the bindings correctly. These are useful when writing device sources; getting &lt;br /&gt;
the DT checks to pass is also mandatory for upstream inclusion of a DTS.&lt;br /&gt;
&lt;br /&gt;
To verify all DTS files built with the selected defconfig options, run:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make dtbs_check&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
To verify a specific DTS, build the DTB target directly and provide the &amp;lt;code&amp;gt;CHECK_DTBS=y&amp;lt;/code&amp;gt; option:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make CHECK_DTBS=y qcom/sm8450-hdk.dtb&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
You can also test a DTS against a specific subset of bindings by providing the &amp;lt;code&amp;gt;DT_SCHEMA_FILES&amp;lt;/code&amp;gt; variable as mentioned in the previous section:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make CHECK_DTBS=y DT_SCHEMA_FILES=trivial-devices.yaml qcom/sm8450-hdk.dtb&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Working with DTC ==&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;dtc&amp;lt;/code&amp;gt; tool handles compiling DTS files into DTBs, as well as decompiling DTBs back into DTS. (TODO: add instructions)&lt;br /&gt;
&lt;br /&gt;
== See also ==&lt;br /&gt;
&lt;br /&gt;
* From Linux kernel documentation:&lt;br /&gt;
** [https://docs.kernel.org/devicetree/bindings/dts-coding-style.html Devicetree Sources (DTS) Coding Style]&lt;br /&gt;
* On elinux.org:&lt;br /&gt;
** [https://elinux.org/Device_Tree_Reference Device Tree Reference]&lt;br /&gt;
** [https://elinux.org/Device_Tree_Reference Device Tree Usage]&lt;br /&gt;
&lt;br /&gt;
== References ==&lt;br /&gt;
&lt;br /&gt;
todo enable refs extension&lt;br /&gt;
&lt;br /&gt;
[1] https://www.mail-archive.com/linux-embedded@vger.kernel.org/msg01721.html&lt;br /&gt;
[2] https://github.com/torvalds/linux/commit/b85a3ef4ac65169b65fd2fe9bec7912bbf475ba4&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Note&amp;diff=76</id>
		<title>Template:Note</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Note&amp;diff=76"/>
		<updated>2025-02-20T18:09:35Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;!-- Dark-mode colors are defined in the template style --&amp;gt;&amp;lt;templatestyles src=&amp;quot;Note/style.css&amp;quot;/&amp;gt;&amp;lt;!--&lt;br /&gt;
--&amp;gt;&amp;lt;includeonly&amp;gt;{{Icon box&lt;br /&gt;
| box-icons = [[File:Reference icon.svg|20px|link=|Note]]&lt;br /&gt;
| box-text = {{{1}}}&lt;br /&gt;
| border-color = #ac6600&lt;br /&gt;
| border-width = 1px&lt;br /&gt;
| background = #f6efe5&lt;br /&gt;
| class = box-note&lt;br /&gt;
}}&amp;lt;/includeonly&amp;gt;&amp;lt;!--&lt;br /&gt;
&lt;br /&gt;
--&amp;gt;&amp;lt;noinclude&amp;gt;&lt;br /&gt;
&amp;lt;templatedata&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
	&amp;quot;params&amp;quot;: {&lt;br /&gt;
		&amp;quot;1&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Text&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Text to place in the box&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;unbalanced-wikitext&amp;quot;,&lt;br /&gt;
			&amp;quot;required&amp;quot;: true&lt;br /&gt;
		}&lt;br /&gt;
	},&lt;br /&gt;
	&amp;quot;description&amp;quot;: &amp;quot;Note box containing a note.&amp;quot;,&lt;br /&gt;
	&amp;quot;format&amp;quot;: &amp;quot;inline&amp;quot;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/templatedata&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Example ==&lt;br /&gt;
&lt;br /&gt;
 &amp;lt;nowiki&amp;gt;{{note|This is quite &#039;&#039;&#039;note-worthy&#039;&#039;&#039;.}}&amp;lt;/nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
{{note|This is quite &#039;&#039;&#039;note-worthy&#039;&#039;&#039;.}}&lt;br /&gt;
&amp;lt;/noinclude&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=File:Reference_icon.svg&amp;diff=75</id>
		<title>File:Reference icon.svg</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=File:Reference_icon.svg&amp;diff=75"/>
		<updated>2025-02-20T18:08:37Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Icon_box&amp;diff=74</id>
		<title>Template:Icon box</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Icon_box&amp;diff=74"/>
		<updated>2025-02-20T18:07:37Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;includeonly&amp;gt;&amp;lt;table role=&amp;quot;{{{role|text container}}}&amp;quot; style=&amp;quot;color: {{{color|inherit}}}; background-color: {{{background|inherit}}}; border: {{{border-width|1px}}} {{{border-style|solid}}} {{{border-color|#eaecf0}}}; margin: 4px {{#if: {{{margin|}}}|10%|0}}; border-collapse: collapse;&amp;quot;&amp;gt;&amp;lt;tr&amp;gt;&lt;br /&gt;
&amp;lt;td style=&amp;quot;padding: 2px 0 2px 0.9em; text-align: center; line-height: 1;&amp;quot;&amp;gt;&amp;lt;span style=&amp;quot;white-space: nowrap;&amp;quot;&amp;gt;{{{box-icons}}}&amp;lt;/span&amp;gt;&amp;lt;/td&amp;gt;&lt;br /&gt;
&amp;lt;td style=&amp;quot;padding: {{{padding|0.35em}}} 0.9em; width: 100%;&amp;quot;&amp;gt;{{{box-text}}}&amp;lt;/td&amp;gt;&lt;br /&gt;
&amp;lt;/tr&amp;gt;&amp;lt;/table&amp;gt;&amp;lt;/includeonly&amp;gt;&amp;lt;!--&lt;br /&gt;
&lt;br /&gt;
--&amp;gt;&amp;lt;noinclude&amp;gt;&lt;br /&gt;
&amp;lt;templatedata&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
	&amp;quot;params&amp;quot;: {&lt;br /&gt;
		&amp;quot;role&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;HTML role&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;HTML accessible role parameter to add to the box.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;text container&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;color&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Text color&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Text color in any format supported by CSS (hex, rgb(...), ...)&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;inherit&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;background&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Background color&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Background color in any format supported by CSS (hex, rgb(...), ...)&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;inherit&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;border-width&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Border width&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Border width with unit&amp;quot;,&lt;br /&gt;
			&amp;quot;example&amp;quot;: &amp;quot;1px&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;1px&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;border-style&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Border style&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;CSS border-style value&amp;quot;,&lt;br /&gt;
			&amp;quot;example&amp;quot;: &amp;quot;solid&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;solid&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;border-color&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Border color&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Text color in any format supported by CSS (hex, rgb(...), ...)&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;#eaecf0&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;box-icons&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Box icons&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Standard wikitext containing the icons to place inside of the box, see example syntax.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;content&amp;quot;,&lt;br /&gt;
			&amp;quot;suggested&amp;quot;: true&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;padding&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Padding&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Padding to add to the box, with the unit&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;0.35em&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;box-text&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Box text&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Text inside of the box.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;content&amp;quot;,&lt;br /&gt;
			&amp;quot;required&amp;quot;: true&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;margin&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Enable margin&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;If set, adds a margin from the sides of the box.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;boolean&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;false&amp;quot;,&lt;br /&gt;
			&amp;quot;suggested&amp;quot;: true&lt;br /&gt;
		}&lt;br /&gt;
	},&lt;br /&gt;
	&amp;quot;description&amp;quot;: &amp;quot;Floating box with an icon and background. Used for licensing templates, Template:Note and similar boxes.&amp;quot;,&lt;br /&gt;
	&amp;quot;format&amp;quot;: &amp;quot;block&amp;quot;,&lt;br /&gt;
	&amp;quot;paramOrder&amp;quot;: [&lt;br /&gt;
		&amp;quot;box-text&amp;quot;,&lt;br /&gt;
		&amp;quot;box-icons&amp;quot;,&lt;br /&gt;
		&amp;quot;margin&amp;quot;,&lt;br /&gt;
		&amp;quot;color&amp;quot;,&lt;br /&gt;
		&amp;quot;background&amp;quot;,&lt;br /&gt;
		&amp;quot;border-color&amp;quot;,&lt;br /&gt;
		&amp;quot;border-style&amp;quot;,&lt;br /&gt;
		&amp;quot;border-width&amp;quot;,&lt;br /&gt;
		&amp;quot;padding&amp;quot;,&lt;br /&gt;
		&amp;quot;role&amp;quot;&lt;br /&gt;
	]&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/templatedata&amp;gt;&lt;br /&gt;
&amp;lt;/noinclude&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Devicetree&amp;diff=73</id>
		<title>Devicetree</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Devicetree&amp;diff=73"/>
		<updated>2025-02-20T18:07:10Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Navbox devicetree}}&lt;br /&gt;
The &#039;&#039;&#039;devicetree&#039;&#039;&#039; (device tree, DT) is a tree structure that describes the hardware register layout and configuration of a device. In the Linux kernel, as well as in other DT-using projects like U-Boot, it is the primary method of discovering peripherals on embedded platforms such as ARM.&lt;br /&gt;
&lt;br /&gt;
Devicetrees are written in a plaintext format known as the &#039;&#039;&#039;Device Tree Source (DTS)&#039;&#039;&#039; format. The DTS is later compiled into a &#039;&#039;&#039;Device Tree Blob (DTB)&#039;&#039;&#039;; in this form, it can be loaded by software/firmware.&lt;br /&gt;
&lt;br /&gt;
Devicetrees are validated using &#039;&#039;&#039;devicetree schema&#039;&#039;&#039;, which is described in &#039;&#039;&#039;DT bindings&#039;&#039;&#039;; see [[/Bindings]] for more information.&lt;br /&gt;
&lt;br /&gt;
== Introduction ==&lt;br /&gt;
&lt;br /&gt;
An SoC (System-on-Chip) comprises of many subcomponents: timer, clock controller, I2C/SPI controller, GPIO, interrupt controller, SDHCI storage, USB, and so on. Each needs its own driver, and for most parts the exact implementation differs between chip manufacturers. Most of them expose a static range of addresses in MMIO (memory-mapped IO) space that the system can use to communicate with them. &lt;br /&gt;
&lt;br /&gt;
Additionally, there may be other peripherals connected to the system - often through a bus like I2C or SPI, or as a simple device controlled by a GPIO.&lt;br /&gt;
&lt;br /&gt;
On a standard x86 system, peripherals are usually autodetected, either through ACPI, or by being on a bus like PCI or USB. On most embedded platforms like ARM, however,  there is no such autodetection method, and the hardware needs to be described manually.&lt;br /&gt;
&lt;br /&gt;
The solution for this, used by both the Linux kernel, as well as a variety of other projects like U-Boot, is the &#039;&#039;&#039;devicetree&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
The following is a very simple example DTS (device tree source):&lt;br /&gt;
&lt;br /&gt;
{{note|For a full guide to DTS syntax, see [[/DTS syntax guide]].}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
	my_node: node1@1000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foo&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x1000 0x54&amp;gt;;&lt;br /&gt;
		vendor,bar-factor = &amp;lt;0x2a&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
&lt;br /&gt;
	i2c-controller@3000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x3000 0x800&amp;gt;;&lt;br /&gt;
		&lt;br /&gt;
		#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
		#size-cells = &amp;lt;0&amp;gt;;&lt;br /&gt;
		&lt;br /&gt;
		sensor@10 {&lt;br /&gt;
			compatible = &amp;quot;vendor,baz-sensor&amp;quot;;&lt;br /&gt;
			reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
		};&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The devicetree acts like a map of the hardware; it describes where each component is in register space, and stores configuration values for them. It also describes components located on buses like I2C and SPI, and can carry some metadata about the board/device (like the RAM size/base address, model code or chassis type).&lt;br /&gt;
&lt;br /&gt;
Devicetrees are written in the &#039;&#039;&#039;DTS&#039;&#039;&#039; (Device Tree Source) format; the source file can then be compiled into a &#039;&#039;&#039;DTB&#039;&#039;&#039; (Device Tree Blob), which software can parse to get all the necessary information about a given platform.&lt;br /&gt;
&lt;br /&gt;
On modern systems, the bootloader loads the DTB into a set place in memory; the Linux kernel then decodes the information from the DTB and initializes all the components based on it. (On 32-bit ARM, which predates widespread adoption of DTBs and DTB-capable bootloaders, an alternative mechanism exists in Linux to load a DTB appended to the kernel image).&lt;br /&gt;
&lt;br /&gt;
== History ==&lt;br /&gt;
&lt;br /&gt;
The initial version of the devicetree standard was developed as part of the OpenFirmware initiative; from this standard, the Flattened Device Tree (FDT) emerged and was adopted by the Linux kernel for PowerPC platforms. Around 2009, discussions began to include FDT support for ARM[1]. It was eventually added and first device trees began to appear in 2011[2], although the format didn&#039;t see wider usage (especially in vendor kernels) until around 2013/2014.&lt;br /&gt;
&lt;br /&gt;
Nowadays, the devicetree standard is managed by [https://www.devicetree.org/ devicetree.org]; they maintain the latest version of the [https://www.devicetree.org/specifications Devicetree Specification] and the related set of [https://github.com/devicetree-org/dt-schema core DT schema].&lt;br /&gt;
&lt;br /&gt;
Before the introduction of devicetrees, ARM kernels used &#039;&#039;&#039;board files&#039;&#039;&#039;. These were C files stored in &amp;lt;code&amp;gt;arch/arm/mach-*&amp;lt;/code&amp;gt; which served a similar purpose to devicetrees - they contained structures for defining component configuration (&amp;quot;platform data&amp;quot;). Unlike device trees however, they could also define C functions, since they were regular C sources compiled into the kernel. Board files technically still exist (citation needed?), but are no longer in wide use.&lt;br /&gt;
&lt;br /&gt;
== Devicetree sources in the Linux kernel ==&lt;br /&gt;
&lt;br /&gt;
TODO&lt;br /&gt;
&lt;br /&gt;
== Verifying DTS files ==&lt;br /&gt;
&lt;br /&gt;
The Linux kernel has tools for making sure that device tree sources (DTS) use the bindings correctly. These are useful when writing device sources; getting &lt;br /&gt;
the DT checks to pass is also mandatory for upstream inclusion of a DTS.&lt;br /&gt;
&lt;br /&gt;
To verify all DTS files built with the selected defconfig options, run:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make dtbs_check&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
To verify a specific DTS, build the DTB target directly and provide the &amp;lt;code&amp;gt;CHECK_DTBS=y&amp;lt;/code&amp;gt; option:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make CHECK_DTBS=y qcom/sm8450-hdk.dtb&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
You can also test a DTS against a specific subset of bindings by providing the &amp;lt;code&amp;gt;DT_SCHEMA_FILES&amp;lt;/code&amp;gt; variable as mentioned in the previous section:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make CHECK_DTBS=y DT_SCHEMA_FILES=trivial-devices.yaml qcom/sm8450-hdk.dtb&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Working with DTC ==&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;dtc&amp;lt;/code&amp;gt; tool handles compiling DTS files into DTBs, as well as decompiling DTBs back into DTS. (TODO: add instructions)&lt;br /&gt;
&lt;br /&gt;
== See also ==&lt;br /&gt;
&lt;br /&gt;
* From Linux kernel documentation:&lt;br /&gt;
** [https://docs.kernel.org/devicetree/bindings/dts-coding-style.html Devicetree Sources (DTS) Coding Style]&lt;br /&gt;
* On elinux.org:&lt;br /&gt;
** [https://elinux.org/Device_Tree_Reference Device Tree Reference]&lt;br /&gt;
** [https://elinux.org/Device_Tree_Reference Device Tree Usage]&lt;br /&gt;
&lt;br /&gt;
== References ==&lt;br /&gt;
&lt;br /&gt;
todo enable refs extension&lt;br /&gt;
&lt;br /&gt;
[1] https://www.mail-archive.com/linux-embedded@vger.kernel.org/msg01721.html&lt;br /&gt;
[2] https://github.com/torvalds/linux/commit/b85a3ef4ac65169b65fd2fe9bec7912bbf475ba4&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Note&amp;diff=72</id>
		<title>Template:Note</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Note&amp;diff=72"/>
		<updated>2025-02-20T18:06:58Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Created page with &amp;quot;&amp;lt;!-- Dark-mode colors are defined in the template style --&amp;gt;&amp;lt;templatestyles src=&amp;quot;Note/style.css&amp;quot;/&amp;gt;&amp;lt;!-- --&amp;gt;&amp;lt;includeonly&amp;gt;{{Icon box | box-icons = Note | box-text = {{{1}}} | border-color = #ac6600 | border-width = 1px | background = #f6efe5 | class = box-note }}&amp;lt;/includeonly&amp;gt;&amp;lt;!--  --&amp;gt;&amp;lt;noinclude&amp;gt; &amp;lt;templatedata&amp;gt; { 	&amp;quot;params&amp;quot;: { 		&amp;quot;1&amp;quot;: { 			&amp;quot;label&amp;quot;: &amp;quot;Text&amp;quot;, 			&amp;quot;description&amp;quot;: &amp;quot;Text to place in the box&amp;quot;, 			&amp;quot;type&amp;quot;: &amp;quot;unbalanced-wikitext&amp;quot;,...&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;!-- Dark-mode colors are defined in the template style --&amp;gt;&amp;lt;templatestyles src=&amp;quot;Note/style.css&amp;quot;/&amp;gt;&amp;lt;!--&lt;br /&gt;
--&amp;gt;&amp;lt;includeonly&amp;gt;{{Icon box&lt;br /&gt;
| box-icons = [[File:Reference icon.svg|20px|link=|Note]]&lt;br /&gt;
| box-text = {{{1}}}&lt;br /&gt;
| border-color = #ac6600&lt;br /&gt;
| border-width = 1px&lt;br /&gt;
| background = #f6efe5&lt;br /&gt;
| class = box-note&lt;br /&gt;
}}&amp;lt;/includeonly&amp;gt;&amp;lt;!--&lt;br /&gt;
&lt;br /&gt;
--&amp;gt;&amp;lt;noinclude&amp;gt;&lt;br /&gt;
&amp;lt;templatedata&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
	&amp;quot;params&amp;quot;: {&lt;br /&gt;
		&amp;quot;1&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Text&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Text to place in the box&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;unbalanced-wikitext&amp;quot;,&lt;br /&gt;
			&amp;quot;required&amp;quot;: true&lt;br /&gt;
		}&lt;br /&gt;
	},&lt;br /&gt;
	&amp;quot;description&amp;quot;: &amp;quot;Note box containing a note.&amp;quot;,&lt;br /&gt;
	&amp;quot;format&amp;quot;: &amp;quot;inline&amp;quot;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/templatedata&amp;gt;&lt;br /&gt;
&amp;lt;/noinclude&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Note/style.css&amp;diff=71</id>
		<title>Template:Note/style.css</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Note/style.css&amp;diff=71"/>
		<updated>2025-02-20T18:06:55Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Created page with &amp;quot;.skin-theme-clientpref-night .box-note { 	color: #fff !important; 	background-color: #261c09 !important; 	border-color: #6a481c !important; }  @media (prefers-color-scheme: dark) { 	.skin-theme-clientpref-os .box-note { 		color: #fff !important; 		background-color: #261c09 !important; 		border-color: #6a481c !important; 	} }&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;.skin-theme-clientpref-night .box-note {&lt;br /&gt;
	color: #fff !important;&lt;br /&gt;
	background-color: #261c09 !important;&lt;br /&gt;
	border-color: #6a481c !important;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
@media (prefers-color-scheme: dark) {&lt;br /&gt;
	.skin-theme-clientpref-os .box-note {&lt;br /&gt;
		color: #fff !important;&lt;br /&gt;
		background-color: #261c09 !important;&lt;br /&gt;
		border-color: #6a481c !important;&lt;br /&gt;
	}&lt;br /&gt;
}&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Icon_box&amp;diff=70</id>
		<title>Template:Icon box</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Icon_box&amp;diff=70"/>
		<updated>2025-02-20T18:03:11Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: make no margin the default, replace nomargin option with margin option&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;includeonly&amp;gt;&amp;lt;table role=&amp;quot;{{{role|text container}}}&amp;quot; style=&amp;quot;color: {{{color|inherit}}}; background-color: {{{background|inherit}}}; border: {{{border-width|1px}}} {{{border-style|solid}}} {{{border-color|#eaecf0}}}; margin: 4px {{#if: {{{margin|}}}|0|10%}}; border-collapse: collapse;&amp;quot;&amp;gt;&amp;lt;tr&amp;gt;&lt;br /&gt;
&amp;lt;td style=&amp;quot;padding: 2px 0 2px 0.9em; text-align: center; line-height: 1;&amp;quot;&amp;gt;&amp;lt;span style=&amp;quot;white-space: nowrap;&amp;quot;&amp;gt;{{{box-icons}}}&amp;lt;/span&amp;gt;&amp;lt;/td&amp;gt;&lt;br /&gt;
&amp;lt;td style=&amp;quot;padding: {{{padding|0.35em}}} 0.9em; width: 100%;&amp;quot;&amp;gt;{{{box-text}}}&amp;lt;/td&amp;gt;&lt;br /&gt;
&amp;lt;/tr&amp;gt;&amp;lt;/table&amp;gt;&amp;lt;/includeonly&amp;gt;&amp;lt;!--&lt;br /&gt;
&lt;br /&gt;
--&amp;gt;&amp;lt;noinclude&amp;gt;&lt;br /&gt;
&amp;lt;templatedata&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
	&amp;quot;params&amp;quot;: {&lt;br /&gt;
		&amp;quot;role&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;HTML role&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;HTML accessible role parameter to add to the box.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;text container&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;color&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Text color&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Text color in any format supported by CSS (hex, rgb(...), ...)&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;inherit&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;background&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Background color&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Background color in any format supported by CSS (hex, rgb(...), ...)&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;inherit&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;border-width&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Border width&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Border width with unit&amp;quot;,&lt;br /&gt;
			&amp;quot;example&amp;quot;: &amp;quot;1px&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;1px&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;border-style&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Border style&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;CSS border-style value&amp;quot;,&lt;br /&gt;
			&amp;quot;example&amp;quot;: &amp;quot;solid&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;solid&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;border-color&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Border color&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Text color in any format supported by CSS (hex, rgb(...), ...)&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;#eaecf0&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;box-icons&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Box icons&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Standard wikitext containing the icons to place inside of the box, see example syntax.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;content&amp;quot;,&lt;br /&gt;
			&amp;quot;suggested&amp;quot;: true&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;padding&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Padding&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Padding to add to the box, with the unit&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;string&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;0.35em&amp;quot;&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;box-text&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Box text&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Text inside of the box.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;content&amp;quot;,&lt;br /&gt;
			&amp;quot;required&amp;quot;: true&lt;br /&gt;
		},&lt;br /&gt;
		&amp;quot;margin&amp;quot;: {&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Enable margin&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;If set, adds a margin from the sides of the box.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;boolean&amp;quot;,&lt;br /&gt;
			&amp;quot;autovalue&amp;quot;: &amp;quot;false&amp;quot;,&lt;br /&gt;
			&amp;quot;suggested&amp;quot;: true&lt;br /&gt;
		}&lt;br /&gt;
	},&lt;br /&gt;
	&amp;quot;description&amp;quot;: &amp;quot;Floating box with an icon and background. Used for licensing templates, Template:Note and similar boxes.&amp;quot;,&lt;br /&gt;
	&amp;quot;format&amp;quot;: &amp;quot;block&amp;quot;,&lt;br /&gt;
	&amp;quot;paramOrder&amp;quot;: [&lt;br /&gt;
		&amp;quot;box-text&amp;quot;,&lt;br /&gt;
		&amp;quot;box-icons&amp;quot;,&lt;br /&gt;
		&amp;quot;margin&amp;quot;,&lt;br /&gt;
		&amp;quot;color&amp;quot;,&lt;br /&gt;
		&amp;quot;background&amp;quot;,&lt;br /&gt;
		&amp;quot;border-color&amp;quot;,&lt;br /&gt;
		&amp;quot;border-style&amp;quot;,&lt;br /&gt;
		&amp;quot;border-width&amp;quot;,&lt;br /&gt;
		&amp;quot;padding&amp;quot;,&lt;br /&gt;
		&amp;quot;role&amp;quot;&lt;br /&gt;
	]&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/templatedata&amp;gt;&lt;br /&gt;
&amp;lt;/noinclude&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:SyntaxHighlight_header&amp;diff=69</id>
		<title>Template:SyntaxHighlight header</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:SyntaxHighlight_header&amp;diff=69"/>
		<updated>2025-02-20T18:01:51Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: move template source above template data&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;includeonly&amp;gt;&amp;lt;div class=&amp;quot;mw-highlight mainline-syntaxhighlight-header&amp;quot; style=&amp;quot;background: var(--background-color-neutral,#eaecf0); color: var(--color-base,#202122); margin-bottom: -1em; padding: 0.35em 1.05em; border: 1px solid var(--border-color-muted,#dadde3); border-bottom: none; font-family: monospace; font-weight: bold;&amp;quot;&amp;gt;{{{text|{{{1|}}}}}}&amp;lt;/div&amp;gt;&amp;lt;/includeonly&amp;gt;&amp;lt;!--&lt;br /&gt;
&lt;br /&gt;
--&amp;gt;&amp;lt;noinclude&amp;gt;&lt;br /&gt;
&amp;lt;templatedata&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
	&amp;quot;params&amp;quot;: {&lt;br /&gt;
		&amp;quot;text&amp;quot;: {&lt;br /&gt;
			&amp;quot;aliases&amp;quot;: [&lt;br /&gt;
				&amp;quot;1&amp;quot;&lt;br /&gt;
			],&lt;br /&gt;
			&amp;quot;label&amp;quot;: &amp;quot;Text&amp;quot;,&lt;br /&gt;
			&amp;quot;description&amp;quot;: &amp;quot;Text to place in the header.&amp;quot;,&lt;br /&gt;
			&amp;quot;type&amp;quot;: &amp;quot;unbalanced-wikitext&amp;quot;,&lt;br /&gt;
			&amp;quot;required&amp;quot;: true&lt;br /&gt;
		}&lt;br /&gt;
	},&lt;br /&gt;
	&amp;quot;description&amp;quot;: &amp;quot;Header that can be placed before a &amp;lt;syntaxhighlight&amp;gt; tag to e.g. show a filename or block title.&amp;quot;,&lt;br /&gt;
	&amp;quot;format&amp;quot;: &amp;quot;inline&amp;quot;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/templatedata&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Example ==&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&amp;lt;nowiki&amp;gt;&lt;br /&gt;
{{SyntaxHighlight header|foo.dts}}&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	&lt;br /&gt;
	my_node: node1@1000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foo&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x1000 0x54&amp;gt;;&lt;br /&gt;
		vendor,bar-factor = &amp;lt;0x2a&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&amp;lt;/nowiki&amp;gt;&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
{{SyntaxHighlight header|foo.dts}}&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	&lt;br /&gt;
	my_node: node1@1000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foo&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x1000 0x54&amp;gt;;&lt;br /&gt;
		vendor,bar-factor = &amp;lt;0x2a&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&amp;lt;/noinclude&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Devicetree_take_2&amp;diff=68</id>
		<title>User:Knuxify/Draft:Devicetree take 2</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Devicetree_take_2&amp;diff=68"/>
		<updated>2025-02-20T17:47:23Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Navbox devicetree}}&lt;br /&gt;
The &#039;&#039;&#039;devicetree&#039;&#039;&#039; (device tree, DT) is a tree structure that describes the hardware register layout and configuration of a device.&lt;br /&gt;
&lt;br /&gt;
Devicetrees are written in a plaintext format known as the &#039;&#039;&#039;Devicetree Source (DTS)&#039;&#039;&#039; format. The DTS is later compiled into a &#039;&#039;&#039;Devicetree Blob (DTB)&#039;&#039;&#039;; in this form, it can be loaded by software/firmware.&lt;br /&gt;
&lt;br /&gt;
Devicetrees are validated using &#039;&#039;&#039;devicetree schema&#039;&#039;&#039;, which is described in &#039;&#039;&#039;DT bindings&#039;&#039;&#039;; see [[/Bindings]] for more information.&lt;br /&gt;
&lt;br /&gt;
In the Linux kernel, as well as in other DT-using projects like U-Boot, it is the primary method of discovering peripherals on embedded platforms such as ARM.&lt;br /&gt;
&lt;br /&gt;
== Introduction ==&lt;br /&gt;
&lt;br /&gt;
An SoC (System-on-Chip) comprises of many subcomponents: timer, clock controller, I2C/SPI controller, GPIO, interrupt controller, SDHCI storage, USB, and so on. Each needs its own driver, and for most parts the exact implementation differs between chip manufacturers. Most of them expose a static range of addresses in MMIO (memory-mapped IO) space that the system can use to communicate with them. &lt;br /&gt;
&lt;br /&gt;
Additionally, there may be other peripherals connected to the system - often through a bus like I2C or SPI, or as a simple device controlled by a GPIO.&lt;br /&gt;
&lt;br /&gt;
On a standard x86 system, peripherals are usually autodetected, either through ACPI, or by being on a bus like PCI or USB. On most embedded platforms like ARM, however,  there is no such autodetection method, and the hardware needs to be described manually.&lt;br /&gt;
&lt;br /&gt;
The solution for this, used by both the Linux kernel, as well as a variety of other projects like U-Boot, is the &#039;&#039;&#039;devicetree&#039;&#039;&#039;.&lt;br /&gt;
&lt;br /&gt;
The devicetree acts like a map of the hardware; it describes where each component is in register space, and stores configuration values for them. It also describes components located on buses like I2C and SPI, and can carry some metadata about the board/device (like the RAM size/base address, model code or chassis type).&lt;br /&gt;
&lt;br /&gt;
Devicetrees are written in the &#039;&#039;&#039;DTS&#039;&#039;&#039; (Device Tree Source) format; the source file can then be compiled into a &#039;&#039;&#039;DTB&#039;&#039;&#039; (Device Tree Blob), which software can parse to get all the necessary information about a given platform.&lt;br /&gt;
&lt;br /&gt;
On modern systems, the bootloader loads the DTB into a set place in memory; the Linux kernel then decodes the information from the DTB and initializes all the components based on it. (On 32-bit ARM, which predates widespread adoption of DTBs and DTB-capable bootloaders, an alternative mechanism exists in Linux to load a DTB appended to the kernel image).&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Devicetree_take_2&amp;diff=67</id>
		<title>User:Knuxify/Draft:Devicetree take 2</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=User:Knuxify/Draft:Devicetree_take_2&amp;diff=67"/>
		<updated>2025-02-20T09:20:17Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Created page with &amp;quot;{{Navbox devicetree}} The &amp;#039;&amp;#039;&amp;#039;devicetree&amp;#039;&amp;#039;&amp;#039; (device tree, DT) is a tree structure that describes the hardware register layout and configuration of a device.  Devicetrees are written in a plaintext format known as the &amp;#039;&amp;#039;&amp;#039;Devicetree Source (DTS)&amp;#039;&amp;#039;&amp;#039; format. The DTS is later compiled into a &amp;#039;&amp;#039;&amp;#039;Devicetree Blob (DTB)&amp;#039;&amp;#039;&amp;#039;; in this form, it can be loaded by software/firmware.  Devicetrees are validated using &amp;#039;&amp;#039;&amp;#039;devicetree schema&amp;#039;&amp;#039;&amp;#039;, which is described in &amp;#039;&amp;#039;&amp;#039;DT bindings&amp;#039;&amp;#039;&amp;#039;; see /...&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Navbox devicetree}}&lt;br /&gt;
The &#039;&#039;&#039;devicetree&#039;&#039;&#039; (device tree, DT) is a tree structure that describes the hardware register layout and configuration of a device.&lt;br /&gt;
&lt;br /&gt;
Devicetrees are written in a plaintext format known as the &#039;&#039;&#039;Devicetree Source (DTS)&#039;&#039;&#039; format. The DTS is later compiled into a &#039;&#039;&#039;Devicetree Blob (DTB)&#039;&#039;&#039;; in this form, it can be loaded by software/firmware.&lt;br /&gt;
&lt;br /&gt;
Devicetrees are validated using &#039;&#039;&#039;devicetree schema&#039;&#039;&#039;, which is described in &#039;&#039;&#039;DT bindings&#039;&#039;&#039;; see [[/Bindings]] for more information.&lt;br /&gt;
&lt;br /&gt;
In the Linux kernel, as well as in other DT-using projects like U-Boot, it is the primary method of discovering peripherals on embedded platforms such as ARM.&lt;br /&gt;
&lt;br /&gt;
== Introduction ==&lt;br /&gt;
&lt;br /&gt;
On a standard x86 system, peripherals are usually autodetected, through either ACPI, or by being on a bus like PCI or USB (TODO - not actually sure how this works?). On an ARM system, however, things are somewhat more complicated.&lt;br /&gt;
&lt;br /&gt;
A devicetree is a map of the various peripherals that make up an SoC or device;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Devicetree/DTS_syntax&amp;diff=66</id>
		<title>Devicetree/DTS syntax</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Devicetree/DTS_syntax&amp;diff=66"/>
		<updated>2025-02-19T20:03:39Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Navbox devicetree}}&lt;br /&gt;
&lt;br /&gt;
This page serves as a guide to the device tree source (DTS) file syntax.&lt;br /&gt;
&lt;br /&gt;
== TODOs ==&lt;br /&gt;
&lt;br /&gt;
* Quick intro to explain how things are typically laid out in ARM chips, buses like I2C, etc. - how &amp;lt;code&amp;gt;reg&amp;lt;/code&amp;gt; addresses work, how DTS syntax describes this layout&lt;br /&gt;
&lt;br /&gt;
== Basic DTS syntax ==&lt;br /&gt;
&lt;br /&gt;
Here is a very simple DTS file to explain the basics of what you might see in a device tree source file:&lt;br /&gt;
&lt;br /&gt;
{{SyntaxHighlight header|foo.dts}}&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	&lt;br /&gt;
	my_node: node1@1000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foo&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x1000 0x54&amp;gt;;&lt;br /&gt;
		vendor,bar-factor = &amp;lt;0x2a&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
&lt;br /&gt;
	node2@2000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,bar&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x2000 0xa4&amp;gt;;&lt;br /&gt;
		vendor,baz-companion = &amp;lt;&amp;amp;my_node&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
&lt;br /&gt;
	i2c-controller@3000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x3000 0x800&amp;gt;;&lt;br /&gt;
		&lt;br /&gt;
		#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
		#size-cells = &amp;lt;0&amp;gt;;&lt;br /&gt;
		&lt;br /&gt;
		sensor@10 {&lt;br /&gt;
			compatible = &amp;quot;vendor,baz-sensor&amp;quot;;&lt;br /&gt;
			reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
		};&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
In this example, we define an empty DTS; in its root node (&amp;lt;code&amp;gt;/&amp;lt;/code&amp;gt;), we place three nodes: a node named &amp;quot;node1&amp;quot; with a label &amp;quot;my_node&amp;quot; at address 0x1000, a node named &amp;quot;node2&amp;quot; at address 0x2000, and a node named &amp;quot;i2c-controller&amp;quot; at address 0x3000.&lt;br /&gt;
&lt;br /&gt;
A node contains:&lt;br /&gt;
* A &amp;lt;code&amp;gt;compatible&amp;lt;/code&amp;gt; value (here &amp;lt;code&amp;gt;&amp;quot;vendor,foo&amp;quot;&amp;lt;/code&amp;gt;). This specifies what kind of component it is; Linux uses this information to load the correct driver.&lt;br /&gt;
* A &amp;lt;code&amp;gt;reg&amp;lt;/code&amp;gt; value. In this case, the first parameter is the base address in memory (&amp;lt;code&amp;gt;0x1000&amp;lt;/code&amp;gt;), and the second is the size it occupies (&amp;lt;code&amp;gt;0x54&amp;lt;/code&amp;gt;). The amount of cells for the address and size are specified by the &amp;lt;code&amp;gt;#address-cells&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;#size-cells&amp;lt;/code&amp;gt; properties of the root node, respectively.&lt;br /&gt;
** You might notice that the i2c-controller node defines another set of these &amp;lt;code&amp;gt;#address-cells&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;#size-cells&amp;lt;/code&amp;gt; properties - this is because I2C devices contain their own subdevices with addresses ranging from 0x08 to 0x7f (todo verify), and they do not use a size.&lt;br /&gt;
* A custom vendor-specific property, &amp;lt;code&amp;gt;vendor,bar-factor&amp;lt;/code&amp;gt;, which takes a number.&lt;br /&gt;
&lt;br /&gt;
On node 2 there is also a property, &amp;lt;code&amp;gt;vendor,baz-companion&amp;lt;/code&amp;gt;, which takes a pointer to another node - here the one we labeled &amp;quot;my_node&amp;quot;.&lt;br /&gt;
&lt;br /&gt;
== Working with included DTSIs ==&lt;br /&gt;
&lt;br /&gt;
Very often you&#039;ll see &amp;lt;code&amp;gt;#include&amp;lt;/code&amp;gt; directives; these can either include header files (which usually contain constants defined with &amp;lt;code&amp;gt;#define&amp;lt;/code&amp;gt;, similarly to C) or other DTSes. DTS files meant for inclusion are called &#039;&#039;&#039;DTS includes&#039;&#039;&#039; and use the &#039;&#039;&#039;.dtsi&#039;&#039;&#039; file extension. &lt;br /&gt;
&lt;br /&gt;
Usually, an SoC will have a common DTS include with all of the relevant nodes for that SoC. A board&#039;s DTS will then include the SoC DTSI.&lt;br /&gt;
&lt;br /&gt;
As an example, here&#039;s a very bare-bones DTSI for a fictional &amp;quot;FOO1234&amp;quot; SoC:&lt;br /&gt;
&lt;br /&gt;
{{SyntaxHighlight header|foo1234.dtsi}}&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/*&lt;br /&gt;
 * Common DTSI for Foobar FOO1234 System-on-a-Chip.&lt;br /&gt;
 */&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
    cpus {&lt;br /&gt;
		#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
		#size-cells = &amp;lt;0&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
		cpu0: cpu@0 {&lt;br /&gt;
			device_type = &amp;quot;cpu&amp;quot;;&lt;br /&gt;
			compatible = &amp;quot;arm,cortex-a7&amp;quot;;&lt;br /&gt;
			reg = &amp;lt;0&amp;gt;;&lt;br /&gt;
			clock-frequency = &amp;lt;1000000000&amp;gt;;&lt;br /&gt;
		};&lt;br /&gt;
    };&lt;br /&gt;
&lt;br /&gt;
    soc {&lt;br /&gt;
        /* ... */&lt;br /&gt;
&lt;br /&gt;
        i2c1: i2c@3000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x3000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        i2c2: i2c@4000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x4000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        i2c3: i2c@5000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x5000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        /* ... */&lt;br /&gt;
    };&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Here is a DTS for a fictional device named &amp;quot;Quox Haystack&amp;quot; that uses the FOO1234 SoC:&lt;br /&gt;
&lt;br /&gt;
{{SyntaxHighlight header|foo1234-quox-haystack.dts}}&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/*&lt;br /&gt;
 * Device tree source for Quox Haystack based on FOO1234 SoC&lt;br /&gt;
 */&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
#include &amp;quot;foo1234.dtsi&amp;quot;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	compatible = &amp;quot;quox,haystack&amp;quot;, &amp;quot;foobar,foo1234&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
	memory@80000000 {&lt;br /&gt;
		device_type = &amp;quot;memory&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x80000000 0x40000000&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
&amp;amp;i2c1 {&lt;br /&gt;
    clock-frequency = &amp;lt;400000&amp;gt;;&lt;br /&gt;
    status = &amp;quot;okay&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
    sensor@10 {&lt;br /&gt;
		compatible = &amp;quot;foobar,baz-sensor&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Some interesting things to look out for:&lt;br /&gt;
&lt;br /&gt;
* The board DTS includes the SoC DTSI with a &amp;lt;code&amp;gt;#include &amp;quot;foo1234.dtsi&amp;quot;&amp;lt;/code&amp;gt; directive.&lt;br /&gt;
* We re-define the root &amp;lt;code&amp;gt;/&amp;lt;/code&amp;gt; node, and inside of it we place a &amp;lt;code&amp;gt;memory&amp;lt;/code&amp;gt; node. This node, as well as the &amp;lt;code&amp;gt;compatible&amp;lt;/code&amp;gt;, will be merged into the root node of the included DTSI.&lt;br /&gt;
* Outside of the root node, there is a node with a name starting with an ampersand (&amp;lt;code&amp;gt;&amp;amp;i2c1&amp;lt;/code&amp;gt;); this signifies a pointer to a labeled node (see node labels in the previous example). Like with the root node above, the contents of this node will be merged with the contents of the node with this label in the SoC DTSI.&lt;br /&gt;
** A similar effect could be achieved by overriding the &amp;lt;code&amp;gt;i2c1&amp;lt;/code&amp;gt; node under the root node, where it&#039;s located in the SoC DTSI (though the preferred way is to do it with a label - we do it here for demonstration purposes):&lt;br /&gt;
*: {{SyntaxHighlight header|foo1234-quox-haystack.dts}}&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line start=&amp;quot;3&amp;quot;&amp;gt;&lt;br /&gt;
/ {&lt;br /&gt;
	compatible = &amp;quot;quox,haystack&amp;quot;, &amp;quot;foobar,foo1234&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
    /* ... */&lt;br /&gt;
&lt;br /&gt;
	i2c1: i2c@3000 {&lt;br /&gt;
        clock-frequency = &amp;lt;400000&amp;gt;;&lt;br /&gt;
        status = &amp;quot;okay&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
        sensor@10 {&lt;br /&gt;
	    	compatible = &amp;quot;foobar,baz-sensor&amp;quot;;&lt;br /&gt;
	    	reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
	    };&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
For a more visual example - the merged version of these two files would look something like this:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
    compatible = &amp;quot;quox,haystack&amp;quot;, &amp;quot;foobar,foo1234&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
	memory@80000000 {&lt;br /&gt;
		device_type = &amp;quot;memory&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x80000000 0x40000000&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
	&lt;br /&gt;
    cpus {&lt;br /&gt;
		#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
		#size-cells = &amp;lt;0&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
		cpu0: cpu@0 {&lt;br /&gt;
			device_type = &amp;quot;cpu&amp;quot;;&lt;br /&gt;
			compatible = &amp;quot;arm,cortex-a7&amp;quot;;&lt;br /&gt;
			reg = &amp;lt;0&amp;gt;;&lt;br /&gt;
			clock-frequency = &amp;lt;1000000000&amp;gt;;&lt;br /&gt;
		};&lt;br /&gt;
    };&lt;br /&gt;
&lt;br /&gt;
    soc {&lt;br /&gt;
        /* ... */&lt;br /&gt;
&lt;br /&gt;
        i2c1: i2c@3000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x3000 0x800&amp;gt;;&lt;br /&gt;
            clock-frequency = &amp;lt;400000&amp;gt;;&lt;br /&gt;
            status = &amp;quot;okay&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
            sensor@10 {&lt;br /&gt;
                compatible = &amp;quot;foobar,baz-sensor&amp;quot;;&lt;br /&gt;
                reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
            };&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        i2c2: i2c@4000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x4000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        i2c3: i2c@5000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x5000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        /* ... */&lt;br /&gt;
    };&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Devicetree/DTS_syntax&amp;diff=65</id>
		<title>Devicetree/DTS syntax</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Devicetree/DTS_syntax&amp;diff=65"/>
		<updated>2025-02-19T20:03:06Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Navbox devicetree}}&lt;br /&gt;
&lt;br /&gt;
This page serves as a guide to the device tree source (DTS) file syntax.&lt;br /&gt;
&lt;br /&gt;
== TODOs ==&lt;br /&gt;
&lt;br /&gt;
* Look through the whole thing again and rewrite. The writing is rather awkward...&lt;br /&gt;
* Quick intro to explain how things are typically laid out in ARM chips, buses like I2C, etc. - how &amp;lt;code&amp;gt;reg&amp;lt;/code&amp;gt; addresses work, how DTS syntax describes this layout&lt;br /&gt;
&lt;br /&gt;
== Basic DTS syntax ==&lt;br /&gt;
&lt;br /&gt;
Here is a very simple DTS file to explain the basics of what you might see in a device tree source file:&lt;br /&gt;
&lt;br /&gt;
{{SyntaxHighlight header|foo.dts}}&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	&lt;br /&gt;
	my_node: node1@1000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foo&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x1000 0x54&amp;gt;;&lt;br /&gt;
		vendor,bar-factor = &amp;lt;0x2a&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
&lt;br /&gt;
	node2@2000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,bar&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x2000 0xa4&amp;gt;;&lt;br /&gt;
		vendor,baz-companion = &amp;lt;&amp;amp;my_node&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
&lt;br /&gt;
	i2c-controller@3000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x3000 0x800&amp;gt;;&lt;br /&gt;
		&lt;br /&gt;
		#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
		#size-cells = &amp;lt;0&amp;gt;;&lt;br /&gt;
		&lt;br /&gt;
		sensor@10 {&lt;br /&gt;
			compatible = &amp;quot;vendor,baz-sensor&amp;quot;;&lt;br /&gt;
			reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
		};&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
In this example, we define an empty DTS; in its root node (&amp;lt;code&amp;gt;/&amp;lt;/code&amp;gt;), we place three nodes: a node named &amp;quot;node1&amp;quot; with a label &amp;quot;my_node&amp;quot; at address 0x1000, a node named &amp;quot;node2&amp;quot; at address 0x2000, and a node named &amp;quot;i2c-controller&amp;quot; at address 0x3000.&lt;br /&gt;
&lt;br /&gt;
A node contains:&lt;br /&gt;
* A &amp;lt;code&amp;gt;compatible&amp;lt;/code&amp;gt; value (here &amp;lt;code&amp;gt;&amp;quot;vendor,foo&amp;quot;&amp;lt;/code&amp;gt;). This specifies what kind of component it is; Linux uses this information to load the correct driver.&lt;br /&gt;
* A &amp;lt;code&amp;gt;reg&amp;lt;/code&amp;gt; value. In this case, the first parameter is the base address in memory (&amp;lt;code&amp;gt;0x1000&amp;lt;/code&amp;gt;), and the second is the size it occupies (&amp;lt;code&amp;gt;0x54&amp;lt;/code&amp;gt;). The amount of cells for the address and size are specified by the &amp;lt;code&amp;gt;#address-cells&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;#size-cells&amp;lt;/code&amp;gt; properties of the root node, respectively.&lt;br /&gt;
** You might notice that the i2c-controller node defines another set of these &amp;lt;code&amp;gt;#address-cells&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;#size-cells&amp;lt;/code&amp;gt; properties - this is because I2C devices contain their own subdevices with addresses ranging from 0x08 to 0x7f (todo verify), and they do not use a size.&lt;br /&gt;
* A custom vendor-specific property, &amp;lt;code&amp;gt;vendor,bar-factor&amp;lt;/code&amp;gt;, which takes a number.&lt;br /&gt;
&lt;br /&gt;
On node 2 there is also a property, &amp;lt;code&amp;gt;vendor,baz-companion&amp;lt;/code&amp;gt;, which takes a pointer to another node - here the one we labeled &amp;quot;my_node&amp;quot;.&lt;br /&gt;
&lt;br /&gt;
== Working with included DTSIs ==&lt;br /&gt;
&lt;br /&gt;
Very often you&#039;ll see &amp;lt;code&amp;gt;#include&amp;lt;/code&amp;gt; directives; these can either include header files (which usually contain constants defined with &amp;lt;code&amp;gt;#define&amp;lt;/code&amp;gt;, similarly to C) or other DTSes. DTS files meant for inclusion are called &#039;&#039;&#039;DTS includes&#039;&#039;&#039; and use the &#039;&#039;&#039;.dtsi&#039;&#039;&#039; file extension. &lt;br /&gt;
&lt;br /&gt;
Usually, an SoC will have a common DTS include with all of the relevant nodes for that SoC. A board&#039;s DTS will then include the SoC DTSI.&lt;br /&gt;
&lt;br /&gt;
As an example, here&#039;s a very bare-bones DTSI for a fictional &amp;quot;FOO1234&amp;quot; SoC:&lt;br /&gt;
&lt;br /&gt;
{{SyntaxHighlight header|foo1234.dtsi}}&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/*&lt;br /&gt;
 * Common DTSI for Foobar FOO1234 System-on-a-Chip.&lt;br /&gt;
 */&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
    cpus {&lt;br /&gt;
		#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
		#size-cells = &amp;lt;0&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
		cpu0: cpu@0 {&lt;br /&gt;
			device_type = &amp;quot;cpu&amp;quot;;&lt;br /&gt;
			compatible = &amp;quot;arm,cortex-a7&amp;quot;;&lt;br /&gt;
			reg = &amp;lt;0&amp;gt;;&lt;br /&gt;
			clock-frequency = &amp;lt;1000000000&amp;gt;;&lt;br /&gt;
		};&lt;br /&gt;
    };&lt;br /&gt;
&lt;br /&gt;
    soc {&lt;br /&gt;
        /* ... */&lt;br /&gt;
&lt;br /&gt;
        i2c1: i2c@3000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x3000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        i2c2: i2c@4000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x4000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        i2c3: i2c@5000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x5000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        /* ... */&lt;br /&gt;
    };&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Here is a DTS for a fictional device named &amp;quot;Quox Haystack&amp;quot; that uses the FOO1234 SoC:&lt;br /&gt;
&lt;br /&gt;
{{SyntaxHighlight header|foo1234-quox-haystack.dts}}&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/*&lt;br /&gt;
 * Device tree source for Quox Haystack based on FOO1234 SoC&lt;br /&gt;
 */&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
#include &amp;quot;foo1234.dtsi&amp;quot;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	compatible = &amp;quot;quox,haystack&amp;quot;, &amp;quot;foobar,foo1234&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
	memory@80000000 {&lt;br /&gt;
		device_type = &amp;quot;memory&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x80000000 0x40000000&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
&amp;amp;i2c1 {&lt;br /&gt;
    clock-frequency = &amp;lt;400000&amp;gt;;&lt;br /&gt;
    status = &amp;quot;okay&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
    sensor@10 {&lt;br /&gt;
		compatible = &amp;quot;foobar,baz-sensor&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Some interesting things to look out for:&lt;br /&gt;
&lt;br /&gt;
* The board DTS includes the SoC DTSI with a &amp;lt;code&amp;gt;#include &amp;quot;foo1234.dtsi&amp;quot;&amp;lt;/code&amp;gt; directive.&lt;br /&gt;
* We re-define the root &amp;lt;code&amp;gt;/&amp;lt;/code&amp;gt; node, and inside of it we place a &amp;lt;code&amp;gt;memory&amp;lt;/code&amp;gt; node. This node, as well as the &amp;lt;code&amp;gt;compatible&amp;lt;/code&amp;gt;, will be merged into the root node of the included DTSI.&lt;br /&gt;
* Outside of the root node, there is a node with a name starting with an ampersand (&amp;lt;code&amp;gt;&amp;amp;i2c1&amp;lt;/code&amp;gt;); this signifies a pointer to a labeled node (see node labels in the previous example). Like with the root node above, the contents of this node will be merged with the contents of the node with this label in the SoC DTSI.&lt;br /&gt;
** A similar effect could be achieved by overriding the &amp;lt;code&amp;gt;i2c1&amp;lt;/code&amp;gt; node under the root node, where it&#039;s located in the SoC DTSI (though the preferred way is to do it with a label - we do it here for demonstration purposes):&lt;br /&gt;
*: {{SyntaxHighlight header|foo1234-quox-haystack.dts}}&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line start=&amp;quot;3&amp;quot;&amp;gt;&lt;br /&gt;
/ {&lt;br /&gt;
	compatible = &amp;quot;quox,haystack&amp;quot;, &amp;quot;foobar,foo1234&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
    /* ... */&lt;br /&gt;
&lt;br /&gt;
	i2c1: i2c@3000 {&lt;br /&gt;
        clock-frequency = &amp;lt;400000&amp;gt;;&lt;br /&gt;
        status = &amp;quot;okay&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
        sensor@10 {&lt;br /&gt;
	    	compatible = &amp;quot;foobar,baz-sensor&amp;quot;;&lt;br /&gt;
	    	reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
	    };&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
For a more visual example - the merged version of these two files would look something like this:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
    compatible = &amp;quot;quox,haystack&amp;quot;, &amp;quot;foobar,foo1234&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
	memory@80000000 {&lt;br /&gt;
		device_type = &amp;quot;memory&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x80000000 0x40000000&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
	&lt;br /&gt;
    cpus {&lt;br /&gt;
		#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
		#size-cells = &amp;lt;0&amp;gt;;&lt;br /&gt;
&lt;br /&gt;
		cpu0: cpu@0 {&lt;br /&gt;
			device_type = &amp;quot;cpu&amp;quot;;&lt;br /&gt;
			compatible = &amp;quot;arm,cortex-a7&amp;quot;;&lt;br /&gt;
			reg = &amp;lt;0&amp;gt;;&lt;br /&gt;
			clock-frequency = &amp;lt;1000000000&amp;gt;;&lt;br /&gt;
		};&lt;br /&gt;
    };&lt;br /&gt;
&lt;br /&gt;
    soc {&lt;br /&gt;
        /* ... */&lt;br /&gt;
&lt;br /&gt;
        i2c1: i2c@3000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x3000 0x800&amp;gt;;&lt;br /&gt;
            clock-frequency = &amp;lt;400000&amp;gt;;&lt;br /&gt;
            status = &amp;quot;okay&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
            sensor@10 {&lt;br /&gt;
                compatible = &amp;quot;foobar,baz-sensor&amp;quot;;&lt;br /&gt;
                reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
            };&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        i2c2: i2c@4000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x4000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        i2c3: i2c@5000 {&lt;br /&gt;
            compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
            reg = &amp;lt;0x5000 0x800&amp;gt;;&lt;br /&gt;
            status = &amp;quot;disabled&amp;quot;;&lt;br /&gt;
        };&lt;br /&gt;
&lt;br /&gt;
        /* ... */&lt;br /&gt;
    };&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Sidebar/styles.css&amp;diff=64</id>
		<title>Template:Sidebar/styles.css</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Sidebar/styles.css&amp;diff=64"/>
		<updated>2025-02-19T19:48:21Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Undo revision 63 by Knuxify (talk)&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;.sidebar {&lt;br /&gt;
	width: 22em;&lt;br /&gt;
	float: right;&lt;br /&gt;
	clear: right;&lt;br /&gt;
	margin: 0.5em 0 1em 1em;&lt;br /&gt;
	font-size: 88%;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
@media (max-width: 640px) {&lt;br /&gt;
    .sidebar {&lt;br /&gt;
		width: 100% !important;&lt;br /&gt;
		clear: both;&lt;br /&gt;
		float: none !important;&lt;br /&gt;
		margin-left: 0 !important;&lt;br /&gt;
		margin-right: 0 !important;&lt;br /&gt;
	}&lt;br /&gt;
	&lt;br /&gt;
	.sidebar.nomobile {&lt;br /&gt;
		display: none;&lt;br /&gt;
	}&lt;br /&gt;
}&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Sidebar/styles.css&amp;diff=63</id>
		<title>Template:Sidebar/styles.css</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Sidebar/styles.css&amp;diff=63"/>
		<updated>2025-02-19T19:47:49Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;.sidebar {&lt;br /&gt;
	width: 22em;&lt;br /&gt;
	float: right;&lt;br /&gt;
	clear: right;&lt;br /&gt;
	margin: 0 0 1em 1em;&lt;br /&gt;
	font-size: 88%;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
@media (max-width: 640px) {&lt;br /&gt;
    .sidebar {&lt;br /&gt;
		width: 100% !important;&lt;br /&gt;
		clear: both;&lt;br /&gt;
		float: none !important;&lt;br /&gt;
		margin-left: 0 !important;&lt;br /&gt;
		margin-right: 0 !important;&lt;br /&gt;
	}&lt;br /&gt;
	&lt;br /&gt;
	.sidebar.nomobile {&lt;br /&gt;
		display: none;&lt;br /&gt;
	}&lt;br /&gt;
}&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Devicetree&amp;diff=62</id>
		<title>Devicetree</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Devicetree&amp;diff=62"/>
		<updated>2025-02-19T19:46:27Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;{{Navbox devicetree}}&lt;br /&gt;
The &#039;&#039;&#039;devicetree&#039;&#039;&#039; (device tree, DT) is a data structure which holds information about all components present on a device. This data is structured in nested nodes with key/value property pairs for configuration.&lt;br /&gt;
&lt;br /&gt;
In simpler terms - a devicetree tells the kernel (or another DT-compatible piece of software/firmware like a bootloader) where each component is in register space/on an I2C or similar bus, and what settings to use to set it up. It is the basic mechanism for discovering components on embedded platforms, including ARM.&lt;br /&gt;
&lt;br /&gt;
Devicetrees are written in a plaintext format known as the &#039;&#039;&#039;Device Tree Source (DTS)&#039;&#039;&#039; format. The DTS is later compiled into a &#039;&#039;&#039;Device Tree Blob (DTB)&#039;&#039;&#039;; in this form, it can be loaded by software/firmware.&lt;br /&gt;
&lt;br /&gt;
Devicetrees are validated using &#039;&#039;&#039;devicetree schema&#039;&#039;&#039;, which is described by bindings; see [[/Bindings]] for more information.&lt;br /&gt;
&lt;br /&gt;
== History ==&lt;br /&gt;
&lt;br /&gt;
The initial version of the devicetree standard was developed as part of the OpenFirmware initiative; from this standard, the Flattened Device Tree (FDT) emerged and was adopted by the Linux kernel for PowerPC platforms. Around 2009, discussions began to include FDT support for ARM[1]. It was eventually added and first device trees began to appear in 2011[2], although the format didn&#039;t see wider usage (especially in vendor kernels) until around 2013/2014.&lt;br /&gt;
&lt;br /&gt;
Nowadays, the devicetree standard is managed by [https://www.devicetree.org/ devicetree.org]; they maintain the latest version of the [https://www.devicetree.org/specifications Devicetree Specification] and the related set of [https://github.com/devicetree-org/dt-schema core DT schema].&lt;br /&gt;
&lt;br /&gt;
Before the introduction of devicetrees, ARM kernels used &#039;&#039;&#039;board files&#039;&#039;&#039;. These were C files stored in &amp;lt;code&amp;gt;arch/arm/mach-*&amp;lt;/code&amp;gt; which served a similar purpose to devicetrees - they contained structures for defining component configuration (&amp;quot;platform data&amp;quot;). Unlike device trees however, they could also define C functions, since they were regular C sources compiled into the kernel. Board files technically still exist (citation needed?), but are no longer in wide use.&lt;br /&gt;
&lt;br /&gt;
== Device Tree Source (DTS)  basics ==&lt;br /&gt;
&lt;br /&gt;
The following is a simple DTS file to demonstrate the DTS syntax. For a more in-depth syntax guide, see [[Devicetree/DTS syntax]].&lt;br /&gt;
&lt;br /&gt;
{{SyntaxHighlight header|foo.dts}}&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;dts&amp;quot; line&amp;gt;&lt;br /&gt;
/dts-v1/;&lt;br /&gt;
&lt;br /&gt;
/ {&lt;br /&gt;
	#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	#size-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
	&lt;br /&gt;
	my_node: node1@1000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foo&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x1000 0x54&amp;gt;;&lt;br /&gt;
		vendor,bar-factor = &amp;lt;0x2a&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
&lt;br /&gt;
	node2@2000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,bar&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x2000 0xa4&amp;gt;;&lt;br /&gt;
		vendor,baz-companion = &amp;lt;&amp;amp;my_node&amp;gt;;&lt;br /&gt;
	};&lt;br /&gt;
&lt;br /&gt;
	i2c-controller@3000 {&lt;br /&gt;
		compatible = &amp;quot;vendor,foobar-i2c&amp;quot;;&lt;br /&gt;
		reg = &amp;lt;0x3000 0x800&amp;gt;;&lt;br /&gt;
		&lt;br /&gt;
		#address-cells = &amp;lt;1&amp;gt;;&lt;br /&gt;
		#size-cells = &amp;lt;0&amp;gt;;&lt;br /&gt;
		&lt;br /&gt;
		sensor@10 {&lt;br /&gt;
			compatible = &amp;quot;vendor,baz-sensor&amp;quot;;&lt;br /&gt;
			reg = &amp;lt;0x10&amp;gt;;&lt;br /&gt;
		};&lt;br /&gt;
	};&lt;br /&gt;
};&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Verifying DTS files ==&lt;br /&gt;
&lt;br /&gt;
The Linux kernel has tools for making sure that device tree sources (DTS) use the bindings correctly. These are useful when writing device sources; getting &lt;br /&gt;
the DT checks to pass is also mandatory for upstream inclusion of a DTS.&lt;br /&gt;
&lt;br /&gt;
To verify all DTS files built with the selected defconfig options, run:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make dtbs_check&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
To verify a specific DTS, build the DTB target directly and provide the &amp;lt;code&amp;gt;CHECK_DTBS=y&amp;lt;/code&amp;gt; option:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make CHECK_DTBS=y qcom/sm8450-hdk.dtb&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
You can also test a DTS against a specific subset of bindings by providing the &amp;lt;code&amp;gt;DT_SCHEMA_FILES&amp;lt;/code&amp;gt; variable as mentioned in the previous section:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;shell-session&amp;quot;&amp;gt;&lt;br /&gt;
$ make CHECK_DTBS=y DT_SCHEMA_FILES=trivial-devices.yaml qcom/sm8450-hdk.dtb&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Working with DTC ==&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;code&amp;gt;dtc&amp;lt;/code&amp;gt; tool handles compiling DTS files into DTBs, as well as decompiling DTBs back into DTS. (TODO: add instructions)&lt;br /&gt;
&lt;br /&gt;
== See also ==&lt;br /&gt;
&lt;br /&gt;
* From Linux kernel documentation:&lt;br /&gt;
** [https://docs.kernel.org/devicetree/bindings/dts-coding-style.html Devicetree Sources (DTS) Coding Style]&lt;br /&gt;
* On elinux.org:&lt;br /&gt;
** [https://elinux.org/Device_Tree_Reference Device Tree Reference]&lt;br /&gt;
** [https://elinux.org/Device_Tree_Reference Device Tree Usage]&lt;br /&gt;
&lt;br /&gt;
== References ==&lt;br /&gt;
&lt;br /&gt;
todo enable refs extension&lt;br /&gt;
&lt;br /&gt;
[1] https://www.mail-archive.com/linux-embedded@vger.kernel.org/msg01721.html&lt;br /&gt;
[2] https://github.com/torvalds/linux/commit/b85a3ef4ac65169b65fd2fe9bec7912bbf475ba4&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Navbox_devicetree&amp;diff=61</id>
		<title>Template:Navbox devicetree</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Navbox_devicetree&amp;diff=61"/>
		<updated>2025-02-19T19:42:40Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;includeonly&amp;gt;{{navbox&lt;br /&gt;
|header=[[File:Devicetree logo.png|48px]]&amp;lt;br&amp;gt;&amp;lt;span style=&amp;quot;display: block; margin-top: 6px;&amp;quot;&amp;gt;Devicetree&amp;lt;/span&amp;gt;&lt;br /&gt;
|links=&lt;br /&gt;
* [[Devicetree|Introduction]]&lt;br /&gt;
* [[Devicetree/DTS syntax|DTS syntax guide]]&lt;br /&gt;
* [[Devicetree/Bindings|DT bindings]]}}&amp;lt;/includeonly&amp;gt;&amp;lt;!--&lt;br /&gt;
&lt;br /&gt;
--&amp;gt;&amp;lt;noinclude&amp;gt;&lt;br /&gt;
&amp;lt;templatedata&amp;gt;&lt;br /&gt;
{&lt;br /&gt;
	&amp;quot;params&amp;quot;: {},&lt;br /&gt;
	&amp;quot;description&amp;quot;: &amp;quot;Navbox template for Devicetree-related pages.&amp;quot;,&lt;br /&gt;
	&amp;quot;format&amp;quot;: &amp;quot;inline&amp;quot;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/templatedata&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Example ==&lt;br /&gt;
&lt;br /&gt;
{{Navbox devicetree}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/noinclude&amp;gt;&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=Template:Navbox/styles.css&amp;diff=60</id>
		<title>Template:Navbox/styles.css</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=Template:Navbox/styles.css&amp;diff=60"/>
		<updated>2025-02-19T19:42:22Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;.navbox {&lt;br /&gt;
	background-color: var(--background-color-neutral-subtle, #f8f9fa);&lt;br /&gt;
	border: 1px solid var(--border-color-base, #a2a9b1);&lt;br /&gt;
	line-height: 1.4em;&lt;br /&gt;
    text-align: center;&lt;br /&gt;
    max-width: 14em;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
.navbox .navbox-header {&lt;br /&gt;
	padding: 2px;&lt;br /&gt;
	font-size: 1.35em;&lt;br /&gt;
	font-weight: bold;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
.navbox:not(.no-header-bg) .navbox-header {&lt;br /&gt;
	background-color: var(--background-color-neutral, #eaecf0);&lt;br /&gt;
	border-bottom: 1px solid var(--border-color-base, #a2a9b1);&lt;br /&gt;
	padding: 4px;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
.navbox .navbox-content .subheading {&lt;br /&gt;
	padding: 2px;&lt;br /&gt;
	font-size: 1.2em;&lt;br /&gt;
	font-weight: bold;&lt;br /&gt;
	line-height: 1.5em;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
.navbox .navbox-content {&lt;br /&gt;
	padding: 2px;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
.navbox .navbox-content ul,&lt;br /&gt;
.navbox .navbox-content ol {&lt;br /&gt;
	margin: 0.25em 0;&lt;br /&gt;
	list-style-type: none;&lt;br /&gt;
}&lt;br /&gt;
.navbox .navbox-content li {&lt;br /&gt;
	padding: 0.05em 0;&lt;br /&gt;
}&lt;br /&gt;
.navbox .navbox-content li:before {&lt;br /&gt;
	content: &amp;quot;•&amp;quot;;&lt;br /&gt;
	margin-right: 0.35em;&lt;br /&gt;
}&lt;br /&gt;
.navbox .navbox-content li:after {&lt;br /&gt;
	content: &amp;quot;•&amp;quot;;&lt;br /&gt;
	margin-left: 0.35em;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
@media (max-width: 640px) {&lt;br /&gt;
	.navbox { max-width: 100%; }&lt;br /&gt;
}&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
	<entry>
		<id>https://wiki.mainlining.org/index.php?title=File:Devicetree_logo.png&amp;diff=59</id>
		<title>File:Devicetree logo.png</title>
		<link rel="alternate" type="text/html" href="https://wiki.mainlining.org/index.php?title=File:Devicetree_logo.png&amp;diff=59"/>
		<updated>2025-02-19T19:38:27Z</updated>

		<summary type="html">&lt;p&gt;Knuxify: Source: https://github.com/devicetree-org/devicetree-website/blob/main/public/favicon.png&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Summary ==&lt;br /&gt;
Source: https://github.com/devicetree-org/devicetree-website/blob/main/public/favicon.png&lt;/div&gt;</summary>
		<author><name>Knuxify</name></author>
	</entry>
</feed>