commit 0348a3fb574d60875779d5abc3e6ce160d638e06 Author: Joakim Date: Sat May 2 22:12:59 2026 +0200 first commit diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..5c66de5 --- /dev/null +++ b/.gitignore @@ -0,0 +1,29 @@ +# Buildroot output +/build/ +/output/ +*.img +*.tar +*.tar.gz + +# Editor / OS junk +*~ +*.swp +*.swo +.DS_Store +.idea/ +.vscode/ + +# Python +__pycache__/ +*.py[cod] +*$py.class +.pytest_cache/ +.tox/ +.venv/ +*.egg-info/ +dist/ +build/ + +# Local overrides +local.mk +.env diff --git a/.gitmodules b/.gitmodules new file mode 100644 index 0000000..00325ef --- /dev/null +++ b/.gitmodules @@ -0,0 +1,4 @@ +[submodule "buildroot"] + path = buildroot + url = https://github.com/buildroot/buildroot.git + branch = 2025.02.x diff --git a/CREDITS.md b/CREDITS.md new file mode 100644 index 0000000..f711346 --- /dev/null +++ b/CREDITS.md @@ -0,0 +1,69 @@ +# Credits & Prior Art + +Mestre is built on top of substantial work by others. This document records +the specific provenance of vendored code and the people who made the project +feasible from day one. + +## Hardware enablement (X6200) + +### Aether project +**[gdyuldin/AetherX6200Buildroot](https://github.com/gdyuldin/AetherX6200Buildroot)** + +Mestre vendors the following from the Aether project: + +- `br2_external/board/x6200/dts/sun8i-r16-x6200.dts` — device tree +- `br2_external/board/x6200/uboot/uboot.config` — U-Boot defconfig +- `br2_external/board/x6200/uboot/boot.cmd` — U-Boot boot script +- `br2_external/board/x6200/linux/patches/0001-drm-panel-jinglitai-jlt4013a.patch` — + LCD panel driver, forward-ported from Aether's `lcd.patch` + +Aether's project goal (improving the X6200 as a transceiver) differs from +Mestre's (using the X6200 as a control head for other SDRs), but Aether's +upstream-friendly hardware enablement work made this project feasible +without reverse-engineering the vendor kernel. All vendored files retain +their original copyright headers. + +### Linux-sunxi community +**apritzel** (#linux-sunxi @ OFTC) — provided the device-tree guidance for the +X6200, acknowledged in the DTS source itself. + +### LCD panel driver +**Rui Oliveira** and **Oleg Belousov** (2022) — original authors of the +Jinglitai JLT4013A panel driver. Their copyright headers are preserved +in the patch. + +## SDR stack + +### piHPSDR +**John Melton (G0ORX/N6LYT)** and contributors — piHPSDR, the GTK3 SDR +console Mestre wraps. Mestre's design relies on piHPSDR's existing MIDI +control infrastructure, which lets us avoid patching the console itself. +Source: https://github.com/g0orx/pihpsdr + +### WDSP +**Warren Pratt (NR0V)** — the WDSP DSP library that piHPSDR depends on. +Linux port maintained by G0ORX. Source: https://github.com/g0orx/wdsp + +### SoapySDR / SoapyRemote +**Pothosware** and contributors — the vendor- and platform-neutral SDR +support library and its network-transparent extension. +Source: https://github.com/pothosware + +### Hermes-Lite 2 +**Steve Haynal (KF7O)** and the Hermes-Lite 2 community — the +open-hardware HF SDR transceiver Mestre is initially designed to control. +The HL2 is the canonical target, but Mestre should work with any +HPSDR-protocol radio piHPSDR supports. + +## Buildroot + +**The Buildroot project** — the embedded Linux build system Mestre uses. +Mestre tracks the Buildroot 2025.02 LTS line. +Source: https://buildroot.org/ + +## Smaller borrowings + +- The MIDI input bridge concept and initial Python sketch (`mestred`) was + developed during earlier prototyping by the project author against the + Aether-derived image; the production version is rewritten as a proper + Python package but owes its shape to that earlier work. diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..d159169 --- /dev/null +++ b/LICENSE @@ -0,0 +1,339 @@ + GNU GENERAL PUBLIC LICENSE + Version 2, June 1991 + + Copyright (C) 1989, 1991 Free Software Foundation, Inc., + 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed. + + Preamble + + The licenses for most software are designed to take away your +freedom to share and change it. By contrast, the GNU General Public +License is intended to guarantee your freedom to share and change free +software--to make sure the software is free for all its users. This +General Public License applies to most of the Free Software +Foundation's software and to any other program whose authors commit to +using it. (Some other Free Software Foundation software is covered by +the GNU Lesser General Public License instead.) You can apply it to +your programs, too. + + When we speak of free software, we are referring to freedom, not +price. Our General Public Licenses are designed to make sure that you +have the freedom to distribute copies of free software (and charge for +this service if you wish), that you receive source code or can get it +if you want it, that you can change the software or use pieces of it +in new free programs; and that you know you can do these things. + + To protect your rights, we need to make restrictions that forbid +anyone to deny you these rights or to ask you to surrender the rights. +These restrictions translate to certain responsibilities for you if you +distribute copies of the software, or if you modify it. + + For example, if you distribute copies of such a program, whether +gratis or for a fee, you must give the recipients all the rights that +you have. You must make sure that they, too, receive or can get the +source code. And you must show them these terms so they know their +rights. + + We protect your rights with two steps: (1) copyright the software, and +(2) offer you this license which gives you legal permission to copy, +distribute and/or modify the software. + + Also, for each author's protection and ours, we want to make certain +that everyone understands that there is no warranty for this free +software. If the software is modified by someone else and passed on, we +want its recipients to know that what they have is not the original, so +that any problems introduced by others will not reflect on the original +authors' reputations. + + Finally, any free program is threatened constantly by software +patents. We wish to avoid the danger that redistributors of a free +program will individually obtain patent licenses, in effect making the +program proprietary. To prevent this, we have made it clear that any +patent must be licensed for everyone's free use or not licensed at all. + + The precise terms and conditions for copying, distribution and +modification follow. + + GNU GENERAL PUBLIC LICENSE + TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION + + 0. This License applies to any program or other work which contains +a notice placed by the copyright holder saying it may be distributed +under the terms of this General Public License. The "Program", below, +refers to any such program or work, and a "work based on the Program" +means either the Program or any derivative work under copyright law: +that is to say, a work containing the Program or a portion of it, +either verbatim or with modifications and/or translated into another +language. (Hereinafter, translation is included without limitation in +the term "modification".) Each licensee is addressed as "you". + +Activities other than copying, distribution and modification are not +covered by this License; they are outside its scope. The act of +running the Program is not restricted, and the output from the Program +is covered only if its contents constitute a work based on the +Program (independent of having been made by running the Program). +Whether that is true depends on what the Program does. + + 1. You may copy and distribute verbatim copies of the Program's +source code as you receive it, in any medium, provided that you +conspicuously and appropriately publish on each copy an appropriate +copyright notice and disclaimer of warranty; keep intact all the +notices that refer to this License and to the absence of any warranty; +and give any other recipients of the Program a copy of this License +along with the Program. + +You may charge a fee for the physical act of transferring a copy, and +you may at your option offer warranty protection in exchange for a fee. + + 2. You may modify your copy or copies of the Program or any portion +of it, thus forming a work based on the Program, and copy and +distribute such modifications or work under the terms of Section 1 +above, provided that you also meet all of these conditions: + + a) You must cause the modified files to carry prominent notices + stating that you changed the files and the date of any change. + + b) You must cause any work that you distribute or publish, that in + whole or in part contains or is derived from the Program or any + part thereof, to be licensed as a whole at no charge to all third + parties under the terms of this License. + + c) If the modified program normally reads commands interactively + when run, you must cause it, when started running for such + interactive use in the most ordinary way, to print or display an + announcement including an appropriate copyright notice and a + notice that there is no warranty (or else, saying that you provide + a warranty) and that users may redistribute the program under + these conditions, and telling the user how to view a copy of this + License. (Exception: if the Program itself is interactive but + does not normally print such an announcement, your work based on + the Program is not required to print an announcement.) + +These requirements apply to the modified work as a whole. If +identifiable sections of that work are not derived from the Program, +and can be reasonably considered independent and separate works in +themselves, then this License, and its terms, do not apply to those +sections when you distribute them as separate works. But when you +distribute the same sections as part of a whole which is a work based +on the Program, the distribution of the whole must be on the terms of +this License, whose permissions for other licensees extend to the +entire whole, and thus to each and every part regardless of who wrote it. + +Thus, it is not the intent of this section to claim rights or contest +your rights to work written entirely by you; rather, the intent is to +exercise the right to control the distribution of derivative or +collective works based on the Program. + +In addition, mere aggregation of another work not based on the Program +with the Program (or with a work based on the Program) on a volume of +a storage or distribution medium does not bring the other work under +the scope of this License. + + 3. You may copy and distribute the Program (or a work based on it, +under Section 2) in object code or executable form under the terms of +Sections 1 and 2 above provided that you also do one of the following: + + a) Accompany it with the complete corresponding machine-readable + source code, which must be distributed under the terms of Sections + 1 and 2 above on a medium customarily used for software interchange; or, + + b) Accompany it with a written offer, valid for at least three + years, to give any third party, for a charge no more than your + cost of physically performing source distribution, a complete + machine-readable copy of the corresponding source code, to be + distributed under the terms of Sections 1 and 2 above on a medium + customarily used for software interchange; or, + + c) Accompany it with the information you received as to the offer + to distribute corresponding source code. (This alternative is + allowed only for noncommercial distribution and only if you + received the program in object code or executable form with such + an offer, in accord with Subsection b above.) + +The source code for a work means the preferred form of the work for +making modifications to it. For an executable work, complete source +code means all the source code for all modules it contains, plus any +associated interface definition files, plus the scripts used to +control compilation and installation of the executable. However, as a +special exception, the source code distributed need not include +anything that is normally distributed (in either source or binary +form) with the major components (compiler, kernel, and so on) of the +operating system on which the executable runs, unless that component +itself accompanies the executable. + +If distribution of executable or object code is made by offering +access to copy from a designated place, then offering equivalent +access to copy the source code from the same place counts as +distribution of the source code, even though third parties are not +compelled to copy the source along with the object code. + + 4. You may not copy, modify, sublicense, or distribute the Program +except as expressly provided under this License. Any attempt +otherwise to copy, modify, sublicense or distribute the Program is +void, and will automatically terminate your rights under this License. +However, parties who have received copies, or rights, from you under +this License will not have their licenses terminated so long as such +parties remain in full compliance. + + 5. You are not required to accept this License, since you have not +signed it. However, nothing else grants you permission to modify or +distribute the Program or its derivative works. These actions are +prohibited by law if you do not accept this License. Therefore, by +modifying or distributing the Program (or any work based on the +Program), you indicate your acceptance of this License to do so, and +all its terms and conditions for copying, distributing or modifying +the Program or works based on it. + + 6. Each time you redistribute the Program (or any work based on the +Program), the recipient automatically receives a license from the +original licensor to copy, distribute or modify the Program subject to +these terms and conditions. You may not impose any further +restrictions on the recipients' exercise of the rights granted herein. +You are not responsible for enforcing compliance by third parties to +this License. + + 7. If, as a consequence of a court judgment or allegation of patent +infringement or for any other reason (not limited to patent issues), +conditions are imposed on you (whether by court order, agreement or +otherwise) that contradict the conditions of this License, they do not +excuse you from the conditions of this License. If you cannot +distribute so as to satisfy simultaneously your obligations under this +License and any other pertinent obligations, then as a consequence you +may not distribute the Program at all. For example, if a patent +license would not permit royalty-free redistribution of the Program by +all those who receive copies directly or indirectly through you, then +the only way you could satisfy both it and this License would be to +refrain entirely from distribution of the Program. + +If any portion of this section is held invalid or unenforceable under +any particular circumstance, the balance of the section is intended to +apply and the section as a whole is intended to apply in other +circumstances. + +It is not the purpose of this section to induce you to infringe any +patents or other property right claims or to contest validity of any +such claims; this section has the sole purpose of protecting the +integrity of the free software distribution system, which is +implemented by public license practices. Many people have made +generous contributions to the wide range of software distributed +through that system in reliance on consistent application of that +system; it is up to the author/donor to decide if he or she is willing +to distribute software through any other system and a licensee cannot +impose that choice. + +This section is intended to make thoroughly clear what is believed to +be a consequence of the rest of this License. + + 8. If the distribution and/or use of the Program is restricted in +certain countries either by patents or by copyrighted interfaces, the +original copyright holder who places the Program under this License +may add an explicit geographical distribution limitation excluding +those countries, so that distribution is permitted only in or among +countries not thus excluded. In such case, this License incorporates +the limitation as if written in the body of this License. + + 9. The Free Software Foundation may publish revised and/or new versions +of the General Public License from time to time. Such new versions will +be similar in spirit to the present version, but may differ in detail to +address new problems or concerns. + +Each version is given a distinguishing version number. If the Program +specifies a version number of this License which applies to it and "any +later version", you have the option of following the terms and conditions +either of that version or of any later version published by the Free +Software Foundation. If the Program does not specify a version number of +this License, you may choose any version ever published by the Free Software +Foundation. + + 10. If you wish to incorporate parts of the Program into other free +programs whose distribution conditions are different, write to the author +to ask for permission. For software which is copyrighted by the Free +Software Foundation, write to the Free Software Foundation; we sometimes +make exceptions for this. Our decision will be guided by the two goals +of preserving the free status of all derivatives of our free software and +of promoting the sharing and reuse of software generally. + + NO WARRANTY + + 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY +FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN +OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES +PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED +OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS +TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE +PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, +REPAIR OR CORRECTION. + + 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING +WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR +REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, +INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING +OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED +TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY +YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER +PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE +POSSIBILITY OF SUCH DAMAGES. + + END OF TERMS AND CONDITIONS + + How to Apply These Terms to Your New Programs + + If you develop a new program, and you want it to be of the greatest +possible use to the public, the best way to achieve this is to make it +free software which everyone can redistribute and change under these terms. + + To do so, attach the following notices to the program. It is safest +to attach them to the start of each source file to most effectively +convey the exclusion of warranty; and each file should have at least +the "copyright" line and a pointer to where the full notice is found. + + + Copyright (C) + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along + with this program; if not, write to the Free Software Foundation, Inc., + 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + +Also add information on how to contact you by electronic and paper mail. + +If the program is interactive, make it output a short notice like this +when it starts in an interactive mode: + + Gnomovision version 69, Copyright (C) year name of author + Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'. + This is free software, and you are welcome to redistribute it + under certain conditions; type `show c' for details. + +The hypothetical commands `show w' and `show c' should show the appropriate +parts of the General Public License. Of course, the commands you use may +be called something other than `show w' and `show c'; they could even be +mouse-clicks or menu items--whatever suits your program. + +You should also get your employer (if you work as a programmer) or your +school, if any, to sign a "copyright disclaimer" for the program, if +necessary. Here is a sample; alter the names: + + Yoyodyne, Inc., hereby disclaims all copyright interest in the program + `Gnomovision' (which makes passes at compilers) written by James Hacker. + + , 1 April 1989 + Ty Coon, President of Vice + +This General Public License does not permit incorporating your program into +proprietary programs. If your program is a subroutine library, you may +consider it more useful to permit linking proprietary applications with the +library. If this is what you want to do, use the GNU Lesser General +Public License instead of this License. diff --git a/README.md b/README.md new file mode 100644 index 0000000..331a384 --- /dev/null +++ b/README.md @@ -0,0 +1,117 @@ +# Mestre + +> An open-source control head for software-defined radios — built on the Xiegu X6200. + +## What is Mestre? + +Mestre turns a [Xiegu X6200](https://www.xiegu.eu/) into a dedicated, tactile remote control head for any networked SDR transceiver, starting with the [Hermes-Lite 2](http://www.hermeslite.com/). + +The motivation is simple. Concepts like FlexRadio's Maestro prove that a dedicated piece of hardware — real VFO knob, real buttons, no laptop — gives the operating experience that touchscreens and mouse-driven SDR consoles don't. But Maestro is closed, expensive, and locked to the FlexRadio ecosystem. + +Mestre uses a radio you may already own (the X6200) and turns its physical controls into a Maestro-class experience for radios you may already own (HL2, ANAN, anything HPSDR-compatible). Open hardware, open software, open protocol. + +``` +┌─────────────────────────┐ ┌──────────────────────┐ +│ X6200 │ │ Hermes-Lite 2 │ +│ ┌───────────────────┐ │ │ │ +│ │ Knobs, buttons │ │ │ (or any HPSDR rig) │ +│ │ Touchscreen, LCD │ │ │ │ +│ └─────────┬─────────┘ │ └──────────┬───────────┘ +│ │ │ │ +│ ┌─────────▼─────────┐ │ Network (HPSDR) │ +│ │ Mestre service │ │ │ +│ │ (evdev → MIDI) │ │ │ +│ └─────────┬─────────┘ │ │ +│ │ │ │ +│ ┌─────────▼─────────┐ │ │ +│ │ piHPSDR │◄─┼───────────────────────────┘ +│ └───────────────────┘ │ +└─────────────────────────┘ +``` + +## Mestre vs Virtuoso + +The project is **Mestre** — the build system, services, and software stack. + +The product name **Virtuoso** is reserved for when (if!) Mestre actually delivers a Maestro-class experience. It must be earned. + +## Project Status + +🚧 **Early development.** Building the foundation. + +| # | Milestone | Status | +|---|----------------------------------------------------------------------|--------| +| 1 | Boot a recent Buildroot LTS on the X6200 (serial console) | 🟡 In progress | +| 2 | Forward-port LCD panel driver — full display output | ⚪ Planned | +| 3 | piHPSDR running on X6200 with working audio | ⚪ Planned | +| 4 | `mestre` service: evdev → ALSA virtual MIDI bridge | ⚪ Planned | +| 5 | End-to-end: X6200 controlling Hermes-Lite 2 as a control head | ⚪ Planned | +| 6 | First-boot wizard, settings persistence, polished UX | ⚪ Planned | +| ∞ | Earn the right to call it Virtuoso | ⚪ TBD | + +## Architecture + +Mestre is built as a Buildroot-based Linux distribution for the X6200. The system runs three cooperating components: + +- **piHPSDR** — handles the SDR protocol, audio, waterfall, and overall radio UI on the X6200's LCD. Connects over the network to the actual transceiver hardware (HL2 or other HPSDR rig). +- **mestre service** — a small daemon that reads the X6200's physical knobs and buttons via `/dev/input/eventX` and translates them into MIDI control change messages on a virtual ALSA MIDI port. +- **piHPSDR's MIDI mapper** — already built into piHPSDR. Subscribes to the virtual MIDI port and acts on the controls. + +The architecture is deliberately patch-free: piHPSDR is used as-is, and the MIDI protocol is the well-known, stable contract between the two halves. + +## Hardware + +- **Control head**: [Xiegu X6200](https://www.xiegu.eu/) (Allwinner R16 / sun8i-a33, 480×800 LCD, knobs, buttons, internal speaker) +- **Transceiver**: [Hermes-Lite 2](http://www.hermeslite.com/) (open-hardware HF SDR), or any HPSDR-protocol radio supported by piHPSDR + +## Building + +> ⚠️ **Pre-1.0**: build instructions are aspirational while milestone 1 is in progress. + +### Prerequisites + +A recent Linux host with the [Buildroot prerequisites](https://buildroot.org/downloads/manual/manual.html#requirement) installed. Building inside the provided container is also supported. + +### Quickstart + +```bash +git clone --recurse-submodules mestre +cd mestre +./scripts/build.sh +``` + +The resulting `sdcard.img` will appear under `build/images/`. Flash it to a microSD card with `dd` or your tool of choice and boot the X6200 from it. + +### Buildroot version + +Mestre is pinned to **Buildroot 2025.02 LTS** for stability — the LTS line is supported with security and bugfix updates for three years. Bumping is a deliberate, documented choice, not a continuous treadmill. + +## Repository layout + +``` +mestre/ +├── buildroot/ # submodule → Buildroot 2025.02.x +├── br2_external/ # all our Buildroot customisations +│ ├── configs/ # defconfig +│ ├── board/x6200/ # linux config, U-Boot config, DTS, overlay +│ └── package/ # custom packages (mestre service, etc.) +├── docs/ # design notes, hardware notes +├── scripts/ # build wrappers +├── README.md # this file +└── DESIGN.md # architectural decisions +``` + +## Credits & Prior Art + +Mestre stands on the shoulders of others. In particular: + +- **[gdyuldin/AetherX6200Buildroot](https://github.com/gdyuldin/AetherX6200Buildroot)** — the Aether project, from which Mestre inherits the X6200 device tree, U-Boot configuration, and LCD panel driver. Aether's project goal (improving the X6200 as a transceiver) differs from Mestre's (using the X6200 as a control head), but Aether's hardware enablement work made Mestre feasible from day one. Vendored files retain their original copyright headers. +- **apritzel** (#linux-sunxi @ OFTC) — device-tree guidance for the X6200, acknowledged in the DTS source. +- **Rui Oliveira** and **Oleg Belousov** — original authors of the Jinglitai JLT4013A panel driver, forward-ported here for use with current mainline kernels. +- **The piHPSDR project** — the SDR console Mestre wraps. Mestre would not exist without piHPSDR's existing MIDI control infrastructure, which lets us avoid patching the console itself. +- **The OpenHPSDR community** and **Steve Haynal (N0EJV / Hermes-Lite 2)** — for keeping open-protocol SDR alive. + +## License + +GPL-2.0-or-later, matching the kernel-derived components Mestre vendors. +Userland components written specifically for Mestre may be re-licensed (e.g. to MIT) on a per-component basis where doing so doesn't conflict with this overall license; such cases will be marked clearly in the relevant subdirectory. diff --git a/br2_external/Config.in b/br2_external/Config.in new file mode 100644 index 0000000..b7eb7be --- /dev/null +++ b/br2_external/Config.in @@ -0,0 +1,7 @@ +menu "Mestre" + +# Custom packages will be sourced here as they are added. +# Each line should look like: +# source "$BR2_EXTERNAL_MESTRE_PATH/package//Config.in" + +endmenu diff --git a/br2_external/board/x6200/dts/sun8i-r16-x6200.dts b/br2_external/board/x6200/dts/sun8i-r16-x6200.dts new file mode 100644 index 0000000..a8f7228 --- /dev/null +++ b/br2_external/board/x6200/dts/sun8i-r16-x6200.dts @@ -0,0 +1,561 @@ +/dts-v1/; + +/* + * Decompiled, and cleaned up device tree file for the X6200. + * Thanks from #linux-sunxi @ OFTC (https://oftc.net/) + */ + +#include "sun8i-a33.dtsi" + +#include +#include + +/ { + model = "XIEGU Tech X6200 Transceiver"; + compatible = "xiegu,x6200", "allwinner,sun8i-r16"; + + aliases { + serial0 = "/soc/serial@1c28000"; + mmc0 = &mmc0; + mmc2 = &mmc2; + }; + + chosen { + stdout-path = "serial0:115200n8"; + }; + + reserved-memory { + #address-cells = <1>; + #size-cells = <1>; + ranges; + + mali_cma: cma@4a000000 { + compatible = "shared-dma-pool"; + size = <0x8000000>; + alloc-ranges = <0x4a000000 0x8000000>; + reusable; + linux,cma-default; + }; + }; + + mmc1_pwrseq: mmc1-pwrseq { + compatible = "mmc-pwrseq-simple"; + reset-gpios = <&pio 2 0 GPIO_ACTIVE_LOW>; /* PC0 (?) */ + }; + + mmc2_pwrseq: mmc2-pwrseq { + compatible = "mmc-pwrseq-simple"; + reset-gpios = <&pio 2 0x10 GPIO_ACTIVE_LOW>; + }; + + reg_usb0_vbus: usb0_vbus { + compatible = "regulator-fixed"; + regulator-name = "usb0_vbus"; + regulator-min-microvolt = <5000000>; + regulator-max-microvolt = <5000000>; + regulator-always-on; + status = "okay"; + }; + + reg_usb1_vbus: usb1_vbus { + compatible = "regulator-fixed"; + regulator-name = "usb1_vbus"; + regulator-min-microvolt = <5000000>; + regulator-max-microvolt = <5000000>; + regulator-boot-on; + enable-active-high; + gpio = <&r_pio 0 4 GPIO_ACTIVE_HIGH>; + status = "okay"; + }; + + reg_vcc3v3: vcc3v3 { + compatible = "regulator-fixed"; + regulator-name = "vcc3v3"; + regulator-min-microvolt = <3300000>; + regulator-max-microvolt = <3300000>; + }; + + reg_vcc5v0: vcc5v0 { + compatible = "regulator-fixed"; + regulator-name = "vcc5v0"; + regulator-min-microvolt = <5000000>; + regulator-max-microvolt = <5000000>; + }; + + backlight: backlight { + compatible = "pwm-backlight"; + power-supply = <®_vcc5v0>; + // perhaps - replace with original 50000 + pwms = <&pwm 0 10000000 0>; + brightness-levels = <0 10 20 30 40 50 60 70 80 90 100>; + default-brightness-level = <5>; + enable-gpios = <&r_pio 0 6 GPIO_ACTIVE_HIGH>; /* PL6 */ + }; + + spi { + compatible = "spi-gpio"; + #address-cells = <1>; + #size-cells = <0>; + sck-gpios = <&r_pio 0 9 GPIO_ACTIVE_HIGH>; /* PL9 */ + mosi-gpios = <&r_pio 0 8 GPIO_ACTIVE_HIGH>; /* PL8 */ + cs-gpios = <&r_pio 0 7 GPIO_ACTIVE_HIGH>; /* PL7 */ + num-chipselects = <1>; + status = "okay"; + + panel@0 { + compatible = "jinglitai,jlt4013a"; + reg = <0>; + power-supply = <®_vcc3v3>; + reset-gpios = <&r_pio 0 11 GPIO_ACTIVE_LOW>; /* PL11 */ + dcx-gpios = <&r_pio 0 10 GPIO_ACTIVE_HIGH>; /* PL10 */ + backlight = <&backlight>; + spi-max-frequency = <100000>; + + port { + panel_input: endpoint { + remote-endpoint = <&tcon0_out_panel>; + }; + }; + }; + }; + + matrix_keypad { + compatible = "gpio-matrix-keypad"; + row-gpios = <&pio 6 10 0x17>, <&pio 6 7 0x17>, /* PG6-PG10 */ + <&pio 6 6 0x17>, <&pio 6 8 0x17>, + <&pio 6 9 0x17>; + col-gpios = <&pio 4 16 GPIO_ACTIVE_LOW>, /* PE11-PE17 */ + <&pio 4 17 GPIO_ACTIVE_LOW>, + <&pio 4 11 GPIO_ACTIVE_LOW>, + <&pio 4 14 GPIO_ACTIVE_LOW>, + <&pio 4 12 GPIO_ACTIVE_LOW>, + <&pio 4 13 GPIO_ACTIVE_LOW>; + linux,keymap = ; + gpio-activelow; + wakeup-source; + linux,no-autorepeat; + debounce-delay-ms = <25>; + col-scan-delay-us = <1>; + drive-inactive-cols; + }; + + rotary0 { + // Main + compatible = "rotary-encoder"; + gpios = <&pio 1 2 GPIO_ACTIVE_LOW>, /* PB2 */ + <&pio 1 3 GPIO_ACTIVE_LOW>; /* PB3 */ + linux,axis = <0>; + rotary-encoder,encoding = "gray"; + rotary-encoder,relative-axis; + pinctrl-names = "default"; + pinctrl-0 = <&rotary_1_pins>; + }; + + rotary1 { + // VOL + compatible = "rotary-encoder"; + gpios = <&pio 1 6 GPIO_ACTIVE_LOW>, <&pio 1 4 GPIO_ACTIVE_LOW>; + linux,axis = <1>; + rotary-encoder,encoding = "gray"; + rotary-encoder,relative-axis; + pinctrl-names = "default"; + pinctrl-0 = <&rotary_2_pins>; + }; + + rotary2 { + // MFK outer + compatible = "rotary-encoder"; + gpios = <&pio 1 5 GPIO_ACTIVE_LOW>, <&pio 1 7 GPIO_ACTIVE_LOW>; + linux,axis = <2>; + rotary-encoder,encoding = "gray"; + rotary-encoder,relative-axis; + rotary-encoder,steps-per-period = <2>; + pinctrl-names = "default"; + pinctrl-0 = <&rotary_3_pins>; + }; + + rotary3 { + // MFK inner + compatible = "rotary-encoder"; + gpios = <&pio 6 0 GPIO_ACTIVE_LOW>, <&pio 6 1 GPIO_ACTIVE_LOW>; + linux,axis = <3>; + rotary-encoder,encoding = "gray"; + rotary-encoder,relative-axis; + rotary-encoder,steps-per-period = <2>; + pinctrl-names = "default"; + pinctrl-0 = <&rotary_4_pins>; + }; +}; + +&de { + status = "okay"; +}; + +&codec { + status = "okay"; +}; + +&dai { + status = "okay"; +}; + +&ehci0 { + status = "okay"; +}; + +&i2c0 { + status = "okay"; + + compatible = "allwinner,sun6i-a31-i2c"; + + reg = <0x1c2ac00 0x400>; + interrupts = ; + clocks = <&ccu CLK_BUS_I2C0>; + // clock-frequency = <100000>; + resets = <&ccu RST_BUS_I2C0>; +}; + +&i2c0_pins { + function = "i2c0"; +}; + +&i2c1 { + status = "okay"; + + compatible = "allwinner,sun6i-a31-i2c"; + + reg = <0x1c2b000 0x400>; + interrupts = ; + clocks = <&ccu CLK_BUS_I2C1>; + // clock-frequency = <100000>; + resets = <&ccu RST_BUS_I2C1>; + + rtc@51 { + compatible = "nxp,pcf8563"; + reg = <0x51>; + interrupt-parent = <&pio>; + interrupts = <6 13 IRQ_TYPE_EDGE_FALLING>; /* PG13 */ + interrupt-names = "irq"; + irq-gpios = <&pio 6 13 GPIO_ACTIVE_HIGH>; + }; +}; + +&i2c1_pins { + function = "i2c1"; +}; + +&mmc0 { + status = "okay"; + vmmc-supply = <®_dcdc1>; + cd-gpios = <&pio 4 3 GPIO_ACTIVE_LOW>; /* PE3 */ + bus-width = <4>; +}; + +&mmc1 { + status = "disabled"; +}; + +&mmc2 { + status = "okay"; + pinctrl-names = "default"; + pinctrl-0 = <&mmc2_8bit_pins>; + vmmc-supply = <®_dcdc1>; + mmc-pwrseq = <&mmc2_pwrseq>; + bus-width = <8>; + non-removable; + cap-mmc-hw-reset; +}; + +&ohci0 { + status = "okay"; +}; + +&pio { + vcc-pb-supply = <®_vcc3v3>; + vcc-pc-supply = <®_vcc3v3>; + vcc-pd-supply = <®_vcc3v3>; + vcc-pe-supply = <®_vcc3v3>; + vcc-pf-supply = <®_vcc3v3>; + vcc-pg-supply = <®_vcc3v3>; + vcc-ph-supply = <®_vcc3v3>; + vcc-pl-supply = <®_vcc3v3>; + + uart3_pins: uart3-pins { + pins = "PH6", "PH7"; + function = "uart3"; + }; + + usb0_id_detect_pin0: usb0_id_detect_pin@0 { + pins = "PH8"; + function = "gpio_in"; + bias-pull-up; + }; + + usb0_vbus_detect_pin0: usb0_vbus_detect_pin@0 { + pins = "PH9"; + function = "gpio_in"; + bias-pull-down; + }; + + rotary_1_pins: rotary-1-pins { + pins = "PB2", "PB3"; + function = "gpio_in"; + bias-pull-up; + }; + + rotary_2_pins: rotary-2-pins { + pins = "PB4", "PB6"; + function = "gpio_in"; + bias-pull-up; + }; + + rotary_3_pins: rotary-3-pins { + pins = "PB5", "PB7"; + function = "gpio_in"; + bias-pull-up; + }; + + rotary_4_pins: rotary-4-pins { + pins = "PG0", "PG1"; + function = "gpio_in"; + bias-pull-up; + }; +}; + +&pwm { + status = "okay"; + pinctrl-names = "default"; + pinctrl-0 = <&pwm0_pin>; +}; + +&r_rsb { + status = "okay"; + + axp22x: pmic@3a3 { + compatible = "x-powers,axp223"; + reg = <0x3a3>; + interrupt-parent = <&r_intc>; + interrupts = ; + eldoin-supply = <®_dcdc1>; + interrupt-controller; + #interrupt-cells = <1>; + }; +}; + +#include "axp223.dtsi" + +&ac_power_supply { + status = "okay"; +}; + +&battery_power_supply { + status = "okay"; +}; + +®_dcdc1 { + regulator-name = "vcc-3v0"; + regulator-always-on; + regulator-min-microvolt = <3000000>; + regulator-max-microvolt = <3000000>; +}; + +®_dcdc2 { + regulator-name = "vdd-sys"; + regulator-always-on; + regulator-min-microvolt = <900000>; + regulator-max-microvolt = <1400000>; +}; + +®_dcdc3 { + regulator-name = "vdd-cpu"; + regulator-always-on; + regulator-min-microvolt = <900000>; + regulator-max-microvolt = <1400000>; +}; + +®_dcdc4 { + regulator-name = "vdd-gpu"; + regulator-min-microvolt = <700000>; + regulator-max-microvolt = <1100000>; +}; + +®_dcdc5 { + regulator-name = "vcc-dram"; + regulator-always-on; + regulator-min-microvolt = <1500000>; + regulator-max-microvolt = <1500000>; +}; + +®_dc1sw { + regulator-name = "vcc-lcd"; + regulator-always-on; +}; + +®_dc5ldo { + regulator-name = "vdd-cpus"; + regulator-always-on; + regulator-min-microvolt = <900000>; + regulator-max-microvolt = <1400000>; +}; + +®_aldo1 { + regulator-name = "vcc-io"; + regulator-always-on; + regulator-min-microvolt = <3000000>; + regulator-max-microvolt = <3000000>; +}; + +®_aldo2 { + regulator-name = "vdd-dll"; + regulator-always-on; + regulator-min-microvolt = <2350000>; + regulator-max-microvolt = <2650000>; +}; + +®_aldo3 { + regulator-name = "vcc-pll-avcc"; + regulator-always-on; + regulator-min-microvolt = <2700000>; + regulator-max-microvolt = <3300000>; +}; + +®_dldo1 { + regulator-name = "vcc-wifi0"; + regulator-always-on; + regulator-min-microvolt = <3300000>; + regulator-max-microvolt = <3300000>; +}; + +®_dldo2 { + regulator-name = "vcc-wifi1"; + regulator-always-on; + regulator-min-microvolt = <3300000>; + regulator-max-microvolt = <3300000>; +}; + +®_dldo3 { + regulator-name = "vcc-3v0-csi"; + regulator-min-microvolt = <3000000>; + regulator-max-microvolt = <3000000>; +}; + +®_eldo1 { + regulator-name = "vcc-1v2-hsic"; + regulator-min-microvolt = <1200000>; + regulator-max-microvolt = <1200000>; +}; + +®_eldo2 { + regulator-name = "vcc-dsp"; + regulator-min-microvolt = <3000000>; + regulator-max-microvolt = <3000000>; +}; + +®_eldo3 { + regulator-name = "eldo3"; + regulator-min-microvolt = <3000000>; + regulator-max-microvolt = <3000000>; +}; + +®_rtc_ldo { + regulator-always-on; + regulator-min-microvolt = <3000000>; + regulator-max-microvolt = <3000000>; + regulator-name = "rtc_ldo"; +}; + +®_drivevbus { + regulator-name = "usb0-vbus"; + status = "okay"; +}; + +&r_uart { + status = "okay"; + pinctrl-names = "default"; + pinctrl-0 = <&r_uart_pins_a>; +}; + +&sound { + simple-audio-card,routing = "Left DAC", "AIF1 Slot 0 Left", + "Right DAC", "AIF1 Slot 0 Right", + "AIF1 Slot 0 Left ADC", "Left ADC", + "AIF1 Slot 0 Right ADC", "Right ADC"; + status = "okay"; +}; + +&tcon0 { + pinctrl-names = "default"; + pinctrl-0 = <&lcd_rgb666_pins>; + status = "okay"; +}; + +&tcon0_out { + tcon0_out_panel: endpoint@0 { + reg = <0>; + remote-endpoint = <&panel_input>; + }; +}; + +&uart0 { + status = "okay"; + pinctrl-names = "default"; + pinctrl-0 = <&uart0_pb_pins>; +}; + +&uart3 { + status = "okay"; + pinctrl-names = "default"; + pinctrl-0 = <&uart3_pins>; +}; + +&usb_otg { + dr_mode = "host"; + status = "okay"; +}; + +&usbphy { + status = "okay"; + usb0_id_det-gpios = <&pio 7 8 GPIO_ACTIVE_HIGH>; /* PH8 */ + usb0_vbus_power-supply = <&usb_power_supply>; + usb0_vbus-supply = <®_usb0_vbus>; + usb1_vbus-supply = <®_usb1_vbus>; + pinctrl-names = "default"; + pinctrl-0 = <&usb0_id_detect_pin0>; +}; + +&usb_power_supply { + status = "okay"; +}; + +&dphy { + status = "okay"; +}; diff --git a/br2_external/board/x6200/genimage.cfg b/br2_external/board/x6200/genimage.cfg new file mode 100644 index 0000000..158b1d5 --- /dev/null +++ b/br2_external/board/x6200/genimage.cfg @@ -0,0 +1,37 @@ +image boot.vfat { + vfat { + files = { + "zImage", + "sun8i-r16-x6200.dtb", + "boot.scr" + } + extraargs = "-n 'BOOT'" + } + + size = 32M +} + + +image sdcard.img { + hdimage { + } + + partition u-boot { + in-partition-table = "no" + image = "u-boot-sunxi-with-spl.bin" + offset = 8K + size = 1016K # 1MB - 8KB + } + + partition boot { + partition-type = 0xc + bootable = "true" + image = "boot.vfat" + } + + partition rootfs { + partition-type = 0x83 + image = "rootfs.ext4" + } + +} diff --git a/br2_external/board/x6200/linux/linux-midi.fragment b/br2_external/board/x6200/linux/linux-midi.fragment new file mode 100644 index 0000000..750417f --- /dev/null +++ b/br2_external/board/x6200/linux/linux-midi.fragment @@ -0,0 +1,37 @@ +# Mestre kernel config fragment — evdev + ALSA MIDI sequencer +# +# Applied on top of linux.config via BR2_LINUX_KERNEL_CONFIG_FRAGMENT_FILES. +# These symbols are required for mestred (the evdev→ALSA MIDI bridge). +# +# Many of these may already be set in linux.config; the fragment is kept +# separate to make the MIDI dependency explicit and easy to trace. + +# Input subsystem — evdev is the interface mestred reads +CONFIG_INPUT_EVDEV=y +CONFIG_INPUT_KEYBOARD=y +CONFIG_INPUT_MISC=y + +# HID (USB MIDI devices, in case we ever attach one) +CONFIG_HID=y +CONFIG_UHID=y + +# ALSA core +CONFIG_SND=y +CONFIG_SND_TIMER=y +CONFIG_SND_PCM=y + +# ALSA Sequencer — the MIDI bus mestred publishes to +CONFIG_SND_SEQ_DEVICE=y +CONFIG_SND_SEQUENCER=y +CONFIG_SND_SEQ_MIDI=y +CONFIG_SND_SEQ_MIDI_EVENT=y +CONFIG_SND_RAWMIDI=y +CONFIG_SND_DRIVERS=y + +# Virtual soundcard — useful for testing piHPSDR MIDI mapping on the bench +# without needing the actual X6200 input devices. +CONFIG_SND_DUMMY=m + +# Expose kernel config via /proc/config.gz (useful for debugging) +CONFIG_IKCONFIG=y +CONFIG_IKCONFIG_PROC=y diff --git a/br2_external/board/x6200/linux/linux.config b/br2_external/board/x6200/linux/linux.config new file mode 100644 index 0000000..af8ef96 --- /dev/null +++ b/br2_external/board/x6200/linux/linux.config @@ -0,0 +1,442 @@ +CONFIG_SYSVIPC=y +CONFIG_POSIX_MQUEUE=y +CONFIG_WATCH_QUEUE=y +CONFIG_USELIB=y +CONFIG_NO_HZ=y +CONFIG_HIGH_RES_TIMERS=y +CONFIG_BPF_SYSCALL=y +CONFIG_BPF_JIT=y +CONFIG_PREEMPT=y +CONFIG_CGROUPS=y +CONFIG_NAMESPACES=y +CONFIG_BOOT_CONFIG=y +CONFIG_EMBEDDED=y +CONFIG_PERF_EVENTS=y +CONFIG_ARCH_SUNXI=y +# CONFIG_VDSO is not set +CONFIG_SMP=y +CONFIG_NR_CPUS=8 +CONFIG_HOTPLUG_CPU=y +CONFIG_HIGHMEM=y +CONFIG_CPU_FREQ=y +CONFIG_CPU_FREQ_DEFAULT_GOV_PERFORMANCE=y +CONFIG_CPU_FREQ_GOV_POWERSAVE=y +CONFIG_CPU_FREQ_GOV_USERSPACE=y +CONFIG_CPU_FREQ_GOV_ONDEMAND=y +CONFIG_CPU_FREQ_GOV_CONSERVATIVE=y +CONFIG_CPU_FREQ_GOV_SCHEDUTIL=y +CONFIG_CPUFREQ_DT=y +CONFIG_ARM_ALLWINNER_SUN50I_CPUFREQ_NVMEM=y +CONFIG_CPU_IDLE=y +CONFIG_ARM_CPUIDLE=y +CONFIG_ARM_PSCI_CPUIDLE=y +CONFIG_VFP=y +CONFIG_NEON=y +CONFIG_KERNEL_MODE_NEON=y +# CONFIG_SUSPEND is not set +CONFIG_PM=y +# CONFIG_GCC_PLUGINS is not set +CONFIG_MODULES=y +CONFIG_MODULE_UNLOAD=y +# CONFIG_MQ_IOSCHED_KYBER is not set +CONFIG_IOSCHED_BFQ=y +CONFIG_BINFMT_MISC=m +CONFIG_CMA=y +CONFIG_USERFAULTFD=y +CONFIG_NET=y +CONFIG_PACKET=y +CONFIG_UNIX=y +CONFIG_UNIX_DIAG=y +CONFIG_TLS=y +CONFIG_INET=y +CONFIG_IP_PNP=y +CONFIG_IP_PNP_DHCP=y +CONFIG_IP_PNP_BOOTP=y +CONFIG_NET_IPIP=y +# CONFIG_INET_DIAG is not set +# CONFIG_IPV6 is not set +CONFIG_CAN=y +CONFIG_BT=m +CONFIG_BT_RFCOMM=m +CONFIG_BT_BNEP=m +CONFIG_BT_HIDP=m +CONFIG_BT_HCIBTUSB=m +CONFIG_CFG80211=m +CONFIG_CFG80211_DEVELOPER_WARNINGS=y +CONFIG_CFG80211_CERTIFICATION_ONUS=y +# CONFIG_CFG80211_REQUIRE_SIGNED_REGDB is not set +# CONFIG_CFG80211_DEFAULT_PS is not set +# CONFIG_CFG80211_CRDA_SUPPORT is not set +CONFIG_LIB80211_DEBUG=y +CONFIG_MAC80211=m +CONFIG_DEVTMPFS=y +CONFIG_DEVTMPFS_MOUNT=y +CONFIG_ARM_SCMI_PROTOCOL=y +CONFIG_ARM_SCPI_PROTOCOL=y +CONFIG_BLK_DEV_SD=y +CONFIG_ATA=y +CONFIG_AHCI_SUNXI=y +CONFIG_NETDEVICES=y +# CONFIG_NET_VENDOR_ALACRITECH is not set +CONFIG_SUN4I_EMAC=y +# CONFIG_NET_VENDOR_AMAZON is not set +# CONFIG_NET_VENDOR_AQUANTIA is not set +# CONFIG_NET_VENDOR_ARC is not set +# CONFIG_NET_VENDOR_BROADCOM is not set +# CONFIG_NET_VENDOR_CADENCE is not set +# CONFIG_NET_VENDOR_CAVIUM is not set +# CONFIG_NET_VENDOR_CIRRUS is not set +# CONFIG_NET_VENDOR_CORTINA is not set +# CONFIG_NET_VENDOR_EZCHIP is not set +# CONFIG_NET_VENDOR_FARADAY is not set +# CONFIG_NET_VENDOR_GOOGLE is not set +# CONFIG_NET_VENDOR_HISILICON is not set +# CONFIG_NET_VENDOR_HUAWEI is not set +# CONFIG_NET_VENDOR_INTEL is not set +# CONFIG_NET_VENDOR_MARVELL is not set +# CONFIG_NET_VENDOR_MELLANOX is not set +# CONFIG_NET_VENDOR_MICREL is not set +# CONFIG_NET_VENDOR_MICROCHIP is not set +# CONFIG_NET_VENDOR_MICROSEMI is not set +# CONFIG_NET_VENDOR_NI is not set +# CONFIG_NET_VENDOR_NATSEMI is not set +# CONFIG_NET_VENDOR_NETRONOME is not set +# CONFIG_NET_VENDOR_PENSANDO is not set +# CONFIG_NET_VENDOR_QUALCOMM is not set +# CONFIG_NET_VENDOR_RENESAS is not set +# CONFIG_NET_VENDOR_ROCKER is not set +# CONFIG_NET_VENDOR_SAMSUNG is not set +# CONFIG_NET_VENDOR_SEEQ is not set +# CONFIG_NET_VENDOR_SOLARFLARE is not set +# CONFIG_NET_VENDOR_SMSC is not set +# CONFIG_NET_VENDOR_SOCIONEXT is not set +CONFIG_STMMAC_ETH=y +# CONFIG_NET_VENDOR_SYNOPSYS is not set +# CONFIG_NET_VENDOR_VIA is not set +# CONFIG_NET_VENDOR_WIZNET is not set +# CONFIG_NET_VENDOR_XILINX is not set +CONFIG_CAN_SUN4I=y +CONFIG_USB_NET_DRIVERS=m +CONFIG_USB_PEGASUS=m +CONFIG_USB_RTL8152=m +CONFIG_USB_LAN78XX=m +CONFIG_USB_USBNET=m +CONFIG_USB_NET_CDC_EEM=m +# CONFIG_USB_NET_NET1080 is not set +# CONFIG_USB_NET_ZAURUS is not set +# CONFIG_WLAN_VENDOR_ADMTEK is not set +# CONFIG_WLAN_VENDOR_ATH is not set +# CONFIG_WLAN_VENDOR_ATMEL is not set +# CONFIG_WLAN_VENDOR_BROADCOM is not set +# CONFIG_WLAN_VENDOR_CISCO is not set +# CONFIG_WLAN_VENDOR_INTEL is not set +# CONFIG_WLAN_VENDOR_INTERSIL is not set +# CONFIG_WLAN_VENDOR_MARVELL is not set +# CONFIG_WLAN_VENDOR_MEDIATEK is not set +CONFIG_RT2X00=m +CONFIG_RT2500USB=m +CONFIG_RT73USB=m +CONFIG_RT2800USB=m +CONFIG_RT2800USB_RT3573=y +CONFIG_RT2800USB_RT53XX=y +CONFIG_RT2800USB_RT55XX=y +CONFIG_RT2800USB_UNKNOWN=y +CONFIG_RTL8192CU=m +CONFIG_RTL8XXXU=m +CONFIG_RTL8XXXU_UNTESTED=y +# CONFIG_WLAN_VENDOR_RSI is not set +# CONFIG_WLAN_VENDOR_ST is not set +# CONFIG_WLAN_VENDOR_TI is not set +# CONFIG_WLAN_VENDOR_ZYDAS is not set +# CONFIG_WLAN_VENDOR_QUANTENNA is not set +CONFIG_INPUT_FF_MEMLESS=y +CONFIG_INPUT_JOYDEV=m +CONFIG_INPUT_EVDEV=y +CONFIG_KEYBOARD_GPIO=y +CONFIG_KEYBOARD_GPIO_POLLED=y +CONFIG_KEYBOARD_MATRIX=y +CONFIG_KEYBOARD_SUN4I_LRADC=y +CONFIG_INPUT_JOYSTICK=y +CONFIG_INPUT_TOUCHSCREEN=y +CONFIG_TOUCHSCREEN_SUN4I=y +CONFIG_INPUT_MISC=y +CONFIG_INPUT_AXP20X_PEK=y +CONFIG_INPUT_GPIO_ROTARY_ENCODER=y +CONFIG_SERIO_SUN4I_PS2=y +CONFIG_SERIAL_8250=y +CONFIG_SERIAL_8250_CONSOLE=y +CONFIG_SERIAL_8250_NR_UARTS=8 +CONFIG_SERIAL_8250_RUNTIME_UARTS=8 +CONFIG_SERIAL_8250_DW=y +CONFIG_SERIAL_OF_PLATFORM=y +# CONFIG_HW_RANDOM is not set +CONFIG_I2C_CHARDEV=y +CONFIG_I2C_MUX=y +CONFIG_I2C_MV64XXX=y +CONFIG_I2C_SUN6I_P2WI=y +CONFIG_SPI=y +CONFIG_SPI_GPIO=y +CONFIG_SPI_SUN4I=y +CONFIG_SPI_SUN6I=y +CONFIG_PPS_CLIENT_LDISC=m +CONFIG_GPIO_SYSFS=y +CONFIG_POWER_RESET=y +CONFIG_POWER_SUPPLY_DEBUG=y +CONFIG_CHARGER_AXP20X=y +CONFIG_BATTERY_AXP20X=y +CONFIG_AXP20X_POWER=y +CONFIG_THERMAL=y +CONFIG_CPU_THERMAL=y +CONFIG_SUN8I_THERMAL=y +CONFIG_WATCHDOG=y +CONFIG_SUNXI_WATCHDOG=y +CONFIG_SSB=m +CONFIG_BCMA=m +CONFIG_MFD_AC100=y +CONFIG_MFD_AXP20X_I2C=y +CONFIG_MFD_AXP20X_RSB=y +CONFIG_REGULATOR=y +CONFIG_REGULATOR_FIXED_VOLTAGE=y +CONFIG_REGULATOR_AXP20X=y +CONFIG_REGULATOR_GPIO=y +CONFIG_RC_CORE=y +CONFIG_RC_DEVICES=y +CONFIG_IR_SUNXI=y +# CONFIG_MEDIA_CEC_SUPPORT is not set +CONFIG_MEDIA_SUPPORT=m +CONFIG_V4L_MEM2MEM_DRIVERS=y +CONFIG_DRM=y +CONFIG_DRM_MALI_DISPLAY=m +CONFIG_DRM_SUN4I=y +CONFIG_DRM_PANEL_JINGLITAI_JLT4013A=y +CONFIG_DRM_SIMPLE_BRIDGE=y +CONFIG_DRM_LIMA=y +CONFIG_FB=y +CONFIG_FIRMWARE_EDID=y +CONFIG_FB_MODE_HELPERS=y +CONFIG_FB_TILEBLITTING=y +CONFIG_FB_OPENCORES=y +CONFIG_FB_SIMPLE=y +CONFIG_LCD_CLASS_DEVICE=y +CONFIG_BACKLIGHT_CLASS_DEVICE=y +CONFIG_BACKLIGHT_PWM=y +CONFIG_BACKLIGHT_GPIO=y +CONFIG_BACKLIGHT_LED=y +CONFIG_FRAMEBUFFER_CONSOLE=y +CONFIG_FRAMEBUFFER_CONSOLE_ROTATION=y +CONFIG_LOGO=y +CONFIG_SOUND=y +CONFIG_SND=y +CONFIG_SND_DUMMY=m +CONFIG_SND_ALOOP=m +CONFIG_SND_USB_AUDIO=m +CONFIG_SND_USB_UA101=m +CONFIG_SND_USB_CAIAQ=m +CONFIG_SND_USB_CAIAQ_INPUT=y +CONFIG_SND_USB_6FIRE=m +CONFIG_SND_USB_HIFACE=m +CONFIG_SND_BCD2000=m +CONFIG_SND_USB_POD=m +CONFIG_SND_USB_PODHD=m +CONFIG_SND_USB_TONEPORT=m +CONFIG_SND_USB_VARIAX=m +CONFIG_SND_SOC=y +CONFIG_SND_SUN4I_CODEC=y +CONFIG_SND_SUN8I_CODEC=y +CONFIG_SND_SUN8I_CODEC_ANALOG=y +CONFIG_SND_SUN4I_I2S=y +CONFIG_SND_SUN4I_SPDIF=y +CONFIG_SND_SOC_CS42L51_I2C=m +CONFIG_SND_SOC_CS42L52=m +CONFIG_SND_SIMPLE_CARD=y +CONFIG_SND_AUDIO_GRAPH_CARD=y +CONFIG_HID_A4TECH=m +CONFIG_HID_APPLE=m +CONFIG_HID_BELKIN=m +CONFIG_HID_CHERRY=m +CONFIG_HID_CHICONY=m +CONFIG_HID_CYPRESS=m +CONFIG_HID_EZKEY=m +CONFIG_HID_ITE=m +CONFIG_HID_KENSINGTON=m +CONFIG_HID_LOGITECH=m +CONFIG_HID_LOGITECH_HIDPP=m +CONFIG_LOGITECH_FF=y +CONFIG_LOGIRUMBLEPAD2_FF=y +CONFIG_LOGIG940_FF=y +CONFIG_HID_REDRAGON=m +CONFIG_HID_MICROSOFT=m +CONFIG_HID_MONTEREY=m +CONFIG_USB=y +CONFIG_USB_OTG=y +CONFIG_USB_XHCI_HCD=m +CONFIG_USB_EHCI_HCD=y +CONFIG_USB_EHCI_HCD_PLATFORM=y +CONFIG_USB_OHCI_HCD=y +CONFIG_USB_OHCI_HCD_PLATFORM=y +CONFIG_USB_ACM=m +CONFIG_USB_WDM=y +CONFIG_USB_STORAGE=m +CONFIG_USB_STORAGE_REALTEK=m +CONFIG_USB_STORAGE_DATAFAB=m +CONFIG_USB_STORAGE_FREECOM=m +CONFIG_USB_STORAGE_ISD200=m +CONFIG_USB_STORAGE_USBAT=m +CONFIG_USB_STORAGE_SDDR09=m +CONFIG_USB_STORAGE_SDDR55=m +CONFIG_USB_STORAGE_JUMPSHOT=m +CONFIG_USB_STORAGE_ALAUDA=m +CONFIG_USB_STORAGE_ONETOUCH=m +CONFIG_USB_STORAGE_KARMA=m +CONFIG_USB_STORAGE_CYPRESS_ATACB=m +CONFIG_USB_STORAGE_ENE_UB6250=m +CONFIG_USB_UAS=m +CONFIG_USB_MUSB_HDRC=m +CONFIG_USB_MUSB_SUNXI=m +CONFIG_USB_SERIAL=m +CONFIG_USB_SERIAL_GENERIC=y +CONFIG_USB_SERIAL_SIMPLE=m +CONFIG_USB_SERIAL_AIRCABLE=m +CONFIG_USB_SERIAL_ARK3116=m +CONFIG_USB_SERIAL_BELKIN=m +CONFIG_USB_SERIAL_CH341=m +CONFIG_USB_SERIAL_WHITEHEAT=m +CONFIG_USB_SERIAL_DIGI_ACCELEPORT=m +CONFIG_USB_SERIAL_CP210X=m +CONFIG_USB_SERIAL_CYPRESS_M8=m +CONFIG_USB_SERIAL_EMPEG=m +CONFIG_USB_SERIAL_FTDI_SIO=m +CONFIG_USB_SERIAL_VISOR=m +CONFIG_USB_SERIAL_IPAQ=m +CONFIG_USB_SERIAL_IR=m +CONFIG_USB_SERIAL_EDGEPORT=m +CONFIG_USB_SERIAL_EDGEPORT_TI=m +CONFIG_USB_SERIAL_F81232=m +CONFIG_USB_SERIAL_F8153X=m +CONFIG_USB_SERIAL_GARMIN=m +CONFIG_USB_SERIAL_IPW=m +CONFIG_USB_SERIAL_IUU=m +CONFIG_USB_SERIAL_KEYSPAN_PDA=m +CONFIG_USB_SERIAL_KEYSPAN=m +CONFIG_USB_SERIAL_KLSI=m +CONFIG_USB_SERIAL_KOBIL_SCT=m +CONFIG_USB_SERIAL_MCT_U232=m +CONFIG_USB_SERIAL_METRO=m +CONFIG_USB_SERIAL_MOS7720=m +CONFIG_USB_SERIAL_MOS7840=m +CONFIG_USB_SERIAL_MXUPORT=m +CONFIG_USB_SERIAL_NAVMAN=m +CONFIG_USB_SERIAL_PL2303=m +CONFIG_USB_SERIAL_OTI6858=m +CONFIG_USB_SERIAL_QCAUX=m +CONFIG_USB_SERIAL_QUALCOMM=m +CONFIG_USB_SERIAL_SPCP8X5=m +CONFIG_USB_SERIAL_SAFE=m +CONFIG_USB_SERIAL_SAFE_PADDED=y +CONFIG_USB_SERIAL_SIERRAWIRELESS=m +CONFIG_USB_SERIAL_SYMBOL=m +CONFIG_USB_SERIAL_TI=m +CONFIG_USB_SERIAL_CYBERJACK=m +CONFIG_USB_SERIAL_OPTION=m +CONFIG_USB_SERIAL_WISHBONE=m +CONFIG_USB_SERIAL_SSU100=m +CONFIG_USB_SERIAL_QT2=m +CONFIG_USB_SERIAL_UPD78F0730=m +CONFIG_USB_SERIAL_XR=m +CONFIG_NOP_USB_XCEIV=m +CONFIG_USB_GADGET=m +CONFIG_USB_ZERO=m +CONFIG_USB_AUDIO=m +CONFIG_USB_ETH=m +CONFIG_USB_G_NCM=m +CONFIG_USB_GADGETFS=m +CONFIG_USB_FUNCTIONFS=m +CONFIG_USB_MASS_STORAGE=m +CONFIG_USB_G_SERIAL=m +CONFIG_USB_CDC_COMPOSITE=m +CONFIG_USB_G_ACM_MS=m +CONFIG_USB_G_MULTI=m +CONFIG_USB_G_HID=m +CONFIG_TYPEC=y +CONFIG_USB_ROLE_SWITCH=m +CONFIG_MMC=y +CONFIG_MMC_SUNXI=y +CONFIG_LEDS_CLASS=y +CONFIG_LEDS_GPIO=y +CONFIG_LEDS_USER=y +CONFIG_LEDS_TRIGGERS=y +CONFIG_LEDS_TRIGGER_HEARTBEAT=y +CONFIG_LEDS_TRIGGER_DEFAULT_ON=y +CONFIG_RTC_CLASS=y +CONFIG_RTC_HCTOSYS_DEVICE="rtc1" +# CONFIG_RTC_INTF_SYSFS is not set +# CONFIG_RTC_INTF_PROC is not set +CONFIG_RTC_DRV_AC100=y +CONFIG_RTC_DRV_PCF8563=y +CONFIG_RTC_DRV_SUNXI=y +CONFIG_DMADEVICES=y +CONFIG_DMA_SUN6I=y +# CONFIG_VIRTIO_MENU is not set +# CONFIG_VHOST_MENU is not set +CONFIG_STAGING=y +CONFIG_RTLLIB=m +CONFIG_RTL8723BS=m +CONFIG_R8712U=m +CONFIG_R8188EU=m +CONFIG_STAGING_MEDIA=y +CONFIG_VIDEO_SUNXI=y +CONFIG_VIDEO_SUNXI_CEDRUS=m +CONFIG_MAILBOX=y +# CONFIG_IOMMU_SUPPORT is not set +CONFIG_DEVFREQ_GOV_PERFORMANCE=y +CONFIG_DEVFREQ_GOV_POWERSAVE=y +CONFIG_DEVFREQ_GOV_USERSPACE=y +CONFIG_DEVFREQ_GOV_PASSIVE=y +CONFIG_IIO=y +CONFIG_AXP20X_ADC=y +CONFIG_PWM=y +CONFIG_PWM_SUN4I=y +CONFIG_PHY_SUN4I_USB=y +CONFIG_PHY_SUN9I_USB=y +CONFIG_NVMEM_SUNXI_SID=y +CONFIG_EXT4_FS=y +CONFIG_OVERLAY_FS=m +CONFIG_VFAT_FS=y +CONFIG_TMPFS=y +CONFIG_NFS_FS=y +CONFIG_NFS_V3_ACL=y +CONFIG_NFS_V4=y +CONFIG_ROOT_NFS=y +CONFIG_NLS_CODEPAGE_437=y +CONFIG_NLS_ISO8859_1=y +CONFIG_CRYPTO_RSA=y +CONFIG_CRYPTO_LZO=y +CONFIG_CRYPTO_LZ4=y +CONFIG_CRYPTO_CURVE25519_NEON=m +CONFIG_CRYPTO_GHASH_ARM_CE=m +CONFIG_CRYPTO_NHPOLY1305_NEON=m +CONFIG_CRYPTO_POLY1305_ARM=m +CONFIG_CRYPTO_SHA1_ARM_NEON=m +CONFIG_CRYPTO_SHA1_ARM_CE=m +CONFIG_CRYPTO_SHA2_ARM_CE=m +CONFIG_CRYPTO_SHA512_ARM=m +CONFIG_CRYPTO_AES_ARM=m +CONFIG_CRYPTO_AES_ARM_BS=m +CONFIG_CRYPTO_AES_ARM_CE=m +CONFIG_CRYPTO_CHACHA20_NEON=m +CONFIG_CRYPTO_CRC32_ARM_CE=m +CONFIG_CRYPTO_DEV_SUN4I_SS=y +CONFIG_CRYPTO_DEV_SUN4I_SS_PRNG=y +CONFIG_CRYPTO_DEV_SUN8I_CE=y +CONFIG_CRYPTO_DEV_SUN8I_SS=m +CONFIG_ASYMMETRIC_KEY_TYPE=y +CONFIG_ASYMMETRIC_PUBLIC_KEY_SUBTYPE=y +CONFIG_X509_CERTIFICATE_PARSER=y +CONFIG_PKCS7_MESSAGE_PARSER=y +CONFIG_SYSTEM_TRUSTED_KEYRING=y +CONFIG_DMA_CMA=y +CONFIG_PRINTK_TIME=y +CONFIG_MAGIC_SYSRQ=y +CONFIG_MAGIC_SYSRQ_SERIAL_SEQUENCE="B" +CONFIG_DEBUG_FS=y +# CONFIG_FTRACE is not set diff --git a/br2_external/board/x6200/linux/patches/0001-drm-panel-jinglitai-jlt4013a.patch b/br2_external/board/x6200/linux/patches/0001-drm-panel-jinglitai-jlt4013a.patch new file mode 100644 index 0000000..0687848 --- /dev/null +++ b/br2_external/board/x6200/linux/patches/0001-drm-panel-jinglitai-jlt4013a.patch @@ -0,0 +1,589 @@ +From: Vendored from gdyuldin/AetherX6200Buildroot (GPL-2.0) +Source: https://github.com/gdyuldin/AetherX6200Buildroot +Original authors: Rui Oliveira (2022), Oleg Belousov (2022) + +Adds driver for the Jinglitai JLT4013A LCD panel used in the Xiegu X6200. + +This patch was written against a ~6.1-era kernel. It may require minor +forward-porting for 6.6 (panel/Kconfig line offsets may have shifted as +new panel drivers were added upstream). The core driver file +(panel-jinglitai-jlt4013a.c) should apply cleanly. + +NOTE: Milestone 1 (serial console boot) does not require this patch. +If the patch fails to apply, comment out BR2_LINUX_KERNEL_PATCH in the +defconfig and address the LCD driver in Milestone 2. +--- + +diff -Naur orig/drivers/gpu/drm/panel/Kconfig my/drivers/gpu/drm/panel/Kconfig +--- orig/drivers/gpu/drm/panel/Kconfig 2023-01-12 14:00:49.000000000 +0300 ++++ my/drivers/gpu/drm/panel/Kconfig 2023-01-30 03:24:48.108365590 +0300 +@@ -717,4 +717,8 @@ + Say Y here if you want to enable support for the Xinpeng + XPP055C272 controller for 720x1280 LCD panels with MIPI/RGB/SPI + system interfaces. ++ ++config DRM_PANEL_JINGLITAI_JLT4013A ++ tristate "Jinglitai JLT4013A panel driver" ++ + endmenu +diff -Naur orig/drivers/gpu/drm/panel/Makefile my/drivers/gpu/drm/panel/Makefile +--- orig/drivers/gpu/drm/panel/Makefile 2023-01-12 14:00:49.000000000 +0300 ++++ my/drivers/gpu/drm/panel/Makefile 2023-01-30 03:23:34.824674091 +0300 +@@ -73,3 +73,4 @@ + obj-$(CONFIG_DRM_PANEL_VISIONOX_RM69299) += panel-visionox-rm69299.o + obj-$(CONFIG_DRM_PANEL_WIDECHIPS_WS2401) += panel-widechips-ws2401.o + obj-$(CONFIG_DRM_PANEL_XINPENG_XPP055C272) += panel-xinpeng-xpp055c272.o ++obj-$(CONFIG_DRM_PANEL_JINGLITAI_JLT4013A) += panel-jinglitai-jlt4013a.o +diff -Naur orig/drivers/gpu/drm/panel/panel-jinglitai-jlt4013a.c my/drivers/gpu/drm/panel/panel-jinglitai-jlt4013a.c +--- orig/drivers/gpu/drm/panel/panel-jinglitai-jlt4013a.c 1970-01-01 03:00:00.000000000 +0300 ++++ my/drivers/gpu/drm/panel/panel-jinglitai-jlt4013a.c 2023-01-30 03:22:15.521007934 +0300 +@@ -0,0 +1,549 @@ ++// SPDX-License-Identifier: GPL-2.0 ++/* ++ * Driver for the Jinglitai JLT4013A LCD Panel. ++ * ++ * Copyright (C) Rui Oliveira 2022 ++ * Copyright (C) Oleg Belousov 2022 ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#define ST7701S_SWRESET 0x01 ++#define ST7701S_SLPOUT 0x11 ++#define ST7701S_DISPOFF 0x28 ++#define ST7701S_DISPON 0x29 ++#define ST7701S_COLMOD 0x3A ++ ++#define ST7701S_CN2BKxSEL 0xFF ++ ++/* BK0 */ ++ ++#define ST7701S_LNESET 0xC0 ++#define ST7701S_PORCTRL 0xC1 ++#define ST7701S_INVSET 0xC2 ++#define ST7701S_PVGAMCTRL 0xB0 ++#define ST7701S_NVGAMCTRL 0xB1 ++ ++/* BK1 */ ++ ++#define ST7701S_VRHS 0xB0 ++#define ST7701S_VCOM 0xB1 ++#define ST7701S_VGHSS 0xB2 ++#define ST7701S_TESTCMD 0xB3 ++#define ST7701S_VGLS 0xB5 ++#define ST7701S_PWCTRL1 0xB7 ++#define ST7701S_PWCTRL2 0xB8 ++#define ST7701S_PWCTRL3 0xB9 ++#define ST7701S_SPD1 0xC1 ++#define ST7701S_SPD2 0xC2 ++#define ST7701S_MIPISET1 0xD0 ++ ++#define ST7701S_TRY(val, func) \ ++ do { \ ++ if ((val = (func))) { \ ++ pr_warn("Jinglitai JLT4013A: SPI write failed with error %d\n", \ ++ val); \ ++ return val; \ ++ } \ ++ } while (0) ++ ++static const struct of_device_id jlt4013a_of_match[] = { ++ { .compatible = "sitronix,st7701s" }, ++ { .compatible = "jinglitai,jlt4013a" }, ++ { /* sentinel */ } ++}; ++MODULE_DEVICE_TABLE(of, jlt4013a_of_match); ++ ++static const struct drm_display_mode jlt4013a_default_display_mode = { ++ .clock = 27500, ++ .hdisplay = 480, /* x */ ++ .hsync_start = 480 + 38, /* x + ri */ ++ .hsync_end = 480 + 38 + 12, /* x + ri + hs */ ++ .htotal = 480 + 38 + 12 + 12, /* x + ri + hs + le */ ++ .vdisplay = 800, /* y */ ++ .vsync_start = 800 + 18, /* y + lo */ ++ .vsync_end = 800 + 18 + 8, /* y + lo + vs */ ++ .vtotal = 800 + 18 + 8 + 17, /* y + lo + vs + up */ ++ .width_mm = 52, ++ .height_mm = 86, ++}; ++ ++ ++struct jlt4013a { ++ struct drm_panel panel; ++ struct spi_device *spi; ++ struct gpio_desc *reset; ++ struct gpio_desc *dcx; ++ struct regulator *supply; ++}; ++ ++static int st7701s_spi_write(struct jlt4013a *ctx, u8 data) ++{ ++ struct spi_transfer xfer = {}; ++ struct spi_message msg; ++ ++ spi_message_init(&msg); ++ ++ xfer.tx_buf = &data; ++ xfer.bits_per_word = 8; ++ xfer.len = sizeof(data); ++ ++ spi_message_add_tail(&xfer, &msg); ++ return spi_sync(ctx->spi, &msg); ++} ++ ++static int st7701s_write_command(struct jlt4013a *ctx, u8 cmd) ++{ ++ // pr_info("Jinglitai JLT4013A: Writing SPI command with value %x\n", cmd); ++ ++ gpiod_set_value(ctx->dcx, 0); ++ ++ return st7701s_spi_write(ctx, cmd); ++} ++ ++static int st7701s_write_data(struct jlt4013a *ctx, u8 cmd) ++{ ++ // pr_info("Jinglitai JLT4013A: Writing SPI data with value %x\n", cmd); ++ ++ gpiod_set_value(ctx->dcx, 1); ++ ++ return st7701s_spi_write(ctx, cmd); ++} ++ ++static inline struct jlt4013a *panel_to_jlt4013a(struct drm_panel *panel) ++{ ++ return container_of(panel, struct jlt4013a, panel); ++} ++ ++static int jlt4013a_prepare(struct drm_panel *panel) ++{ ++ int ret; ++ struct jlt4013a *ctx = panel_to_jlt4013a(panel); ++ ++ /* Enable power supply */ ++ ++ pr_info("Jinglitai JLT4013A: Trying to enable power supply\n"); ++ ret = regulator_enable(ctx->supply); ++ if (ret) { ++ pr_err("Jinglitai JLT4013A: Failed to enable power supply\n"); ++ return ret; ++ } ++ msleep(120); ++ pr_info("Jinglitai JLT4013A: Enabled power supply\n"); ++ ++ /* Reset routine */ ++ pr_info("Jinglitai JLT4013A: Doing the reset routine\n"); ++ gpiod_set_value(ctx->reset, 1); ++ msleep(120); ++ gpiod_set_value(ctx->reset, 0); ++ msleep(120); // Sleep mandated by the datasheet ++ pr_info("Jinglitai JLT4013A: Panel is reset\n"); ++ ++ /* Initialization routine */ ++ pr_info("Jinglitai JLT4013A: Doing the initialization routine\n"); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_SLPOUT)); ++ msleep(120); ++ ++ /* BK0 */ ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_CN2BKxSEL)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x77)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x01)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x10)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_PORCTRL)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, ++ jlt4013a_default_display_mode.vtotal ++ - jlt4013a_default_display_mode.vsync_end)); // mode.vtotal - mode.vsync_end ++ ST7701S_TRY(ret, st7701s_write_data(ctx, ++ jlt4013a_default_display_mode.vsync_start ++ - jlt4013a_default_display_mode.vdisplay)); // mode.vsync_start - mode.vdisplay ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_INVSET)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x31)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x03)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, 0xC3)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x02)); // DataPolarity: negative (The data is input on the negative edge of DOTCLK) ++ ST7701S_TRY(ret, st7701s_write_data(ctx, ++ jlt4013a_default_display_mode.htotal ++ - jlt4013a_default_display_mode.hsync_end)); // HBP = mode.htotal - mode.hsync_end ++ ST7701S_TRY(ret, st7701s_write_data(ctx, ++ jlt4013a_default_display_mode.vsync_start ++ - jlt4013a_default_display_mode.vdisplay)); // VBP = mode.vsync_start - mode.vdisplay ++ ++ /* Something strange */ ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, 0xCC)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x10)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_PVGAMCTRL)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x40)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xC9)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x90)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x0D)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x0F)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x04)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x07)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x07)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x1C)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x04)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x52)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x0F)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xDF)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x26)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xCF)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_NVGAMCTRL)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x40)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xC9)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xCF)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x0C)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x90)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x04)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x07)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x08)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x1B)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x06)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x55)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x13)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x62)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xE7)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xCF)); ++ ++ /* BK1 */ ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_CN2BKxSEL)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x77)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x01)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x11)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_VRHS)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x5B)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_VCOM)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x68)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_VGHSS)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x07)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_TESTCMD)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x80)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_VGLS)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x47)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_PWCTRL1)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x85)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_PWCTRL2)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x21)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_PWCTRL3)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x10)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_SPD1)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x21)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x36)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_SPD2)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x78)); ++ ++ msleep(120); ++ ++ /* Something strange */ ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, 0xE0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x02)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, 0xE1)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x08)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x0A)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x07)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x09)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x33)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x33)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, 0xE2)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, 0xE3)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x33)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x33)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, 0xE4)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x44)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x44)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, 0xE5)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x0E)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x2D)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x10)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x2D)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x0A)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x2D)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x0C)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x2D)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, 0xE6)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x33)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x33)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, 0xE7)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x44)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x44)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, 0xE8)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x0D)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x2D)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x0F)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x2D)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x09)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x2D)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x0B)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x2D)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xA0)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, 0xEB)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x02)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x01)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xE4)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xE4)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x44)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x40)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, 0xEC)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x02)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x01)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, 0xED)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xAB)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x89)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x76)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x54)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x01)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xFF)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xFF)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xFF)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xFF)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xFF)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xFF)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x10)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x45)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x67)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x98)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0xBA)); ++ ++ /* BK disable */ ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_CN2BKxSEL)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x77)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x01)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x00)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_COLMOD)); ++ ST7701S_TRY(ret, st7701s_write_data(ctx, 0x77)); ++ ++ ST7701S_TRY(ret, st7701s_write_command(ctx, ST7701S_DISPON)); ++ ++ msleep(120); ++ ++ pr_info("Jinglitai JLT4013A: Panel is initialized\n"); ++ return ret; ++} ++ ++static int jlt4013a_unprepare(struct drm_panel *panel) ++{ ++ struct jlt4013a *ctx = panel_to_jlt4013a(panel); ++ ++ int ret = regulator_disable(ctx->supply); ++ return ret; ++} ++ ++ ++static int jlt4013a_get_modes(struct drm_panel *panel, ++ struct drm_connector *connector) ++{ ++ static const u32 bus_format = MEDIA_BUS_FMT_RGB888_1X24; ++ static const u32 bus_flags = DRM_BUS_FLAG_PIXDATA_SAMPLE_NEGEDGE; ++ ++ ++ struct drm_display_mode *mode = drm_mode_duplicate( ++ connector->dev, &jlt4013a_default_display_mode); ++ if (mode == NULL) { ++ dev_err(panel->dev, ++ "Jinglitai JLT4013A: Failed to add default mode\n"); ++ return -EAGAIN; ++ } ++ ++ drm_mode_set_name(mode); ++ ++ mode->type = DRM_MODE_TYPE_PREFERRED | DRM_MODE_TYPE_DRIVER; ++ ++ connector->display_info.width_mm = mode->width_mm; ++ connector->display_info.height_mm = mode->height_mm; ++ connector->display_info.bpc = 8; ++ connector->display_info.bus_flags = bus_flags; ++ ++ drm_mode_probed_add(connector, mode); ++ ++ drm_display_info_set_bus_formats(&connector->display_info, &bus_format, ++ 1); ++ ++ return 1; ++} ++ ++static int jlt4013a_enable(struct drm_panel *panel) ++{ ++ return 0; ++} ++ ++static int jlt4013a_disable(struct drm_panel *panel) ++{ ++ return 0; ++} ++ ++static const struct drm_panel_funcs jlt4013afuncs = { ++ .prepare = jlt4013a_prepare, ++ .unprepare = jlt4013a_unprepare, ++ .get_modes = jlt4013a_get_modes, ++ .enable = jlt4013a_enable, ++ .disable = jlt4013a_disable, ++}; ++ ++static int jlt4013a_probe(struct spi_device *spi) ++{ ++ int err; ++ ++ struct device *dev = &spi->dev; ++ ++ struct jlt4013a *ctx = devm_kzalloc(dev, sizeof(*ctx), GFP_KERNEL); ++ if (ctx == NULL) { ++ return -EAGAIN; ++ } ++ ++ ctx->spi = spi; ++ spi_set_drvdata(spi, ctx); ++ ++ ctx->supply = devm_regulator_get(dev, "power"); ++ if (IS_ERR(ctx->supply)) { ++ dev_err(dev, ++ "Jinglitai JLT4013A: Failed to get power supply\n"); ++ return PTR_ERR(ctx->supply); ++ } ++ ++ ctx->reset = devm_gpiod_get(dev, "reset", GPIOD_OUT_LOW); ++ if (IS_ERR(ctx->reset)) { ++ dev_err(dev, "Jinglitai JLT4013A: Failed to get reset GPIO\n"); ++ return PTR_ERR(ctx->reset); ++ } ++ ++ ctx->dcx = devm_gpiod_get(dev, "dcx", GPIOD_OUT_LOW); ++ if (IS_ERR(ctx->dcx)) { ++ dev_err(dev, "Jinglitai JLT4013A: Failed to get dcx GPIO\n"); ++ return PTR_ERR(ctx->dcx); ++ } ++ ++ drm_panel_init(&ctx->panel, dev, &jlt4013afuncs, ++ DRM_MODE_CONNECTOR_DPI); ++ ++ err = drm_panel_of_backlight(&ctx->panel); ++ if (err) ++ return err; ++ ++ drm_panel_add(&ctx->panel); ++ ++ return 0; ++} ++ ++#if LINUX_VERSION_CODE >= KERNEL_VERSION(6,0,0) ++static void jlt4013a_remove(struct spi_device *spi) ++{ ++ struct jlt4013a *ctx = spi_get_drvdata(spi); ++ ++ drm_panel_remove(&(ctx->panel)); ++} ++#else ++static int jlt4013a_remove(struct spi_device *spi) ++{ ++ struct jlt4013a *ctx = spi_get_drvdata(spi); ++ ++ drm_panel_remove(&(ctx->panel)); ++ return 0; ++} ++#endif ++ ++static struct spi_driver jlt4013a_driver = { ++ .probe = jlt4013a_probe, ++ .remove = jlt4013a_remove, ++ .driver = { ++ .name = "jlt4013a", ++ .of_match_table = jlt4013a_of_match, ++ }, ++}; ++module_spi_driver(jlt4013a_driver); ++ ++MODULE_AUTHOR("Rui Oliveira "); ++MODULE_AUTHOR("Oleg Belousov "); ++MODULE_DESCRIPTION("Driver for the Jinglitai JLT4013A LCD Panel"); ++MODULE_LICENSE("GPL v2"); diff --git a/br2_external/board/x6200/uboot/boot.cmd b/br2_external/board/x6200/uboot/boot.cmd new file mode 100644 index 0000000..866c80a --- /dev/null +++ b/br2_external/board/x6200/uboot/boot.cmd @@ -0,0 +1,6 @@ +echo "------------ X6200 boot script ------------" +setenv bootargs console=ttyS0,115200 root=/dev/mmcblk0p2 rootwait panic=10 fbcon=rotate:3 video=VGA:480x800 +fatload mmc 0:1 0x46000000 zImage +fatload mmc 0:1 0x49000000 ${fdtfile} +bootz 0x46000000 - 0x49000000 + diff --git a/br2_external/board/x6200/uboot/uboot.config b/br2_external/board/x6200/uboot/uboot.config new file mode 100644 index 0000000..89c4704 --- /dev/null +++ b/br2_external/board/x6200/uboot/uboot.config @@ -0,0 +1,25 @@ +CONFIG_ARM=y +CONFIG_ARCH_SUNXI=y +CONFIG_DEFAULT_DEVICE_TREE="sun8i-r16-x6200" +CONFIG_SPL=y +CONFIG_IDENT_STRING="" +CONFIG_MACH_SUN8I_A33=y +CONFIG_DRAM_CLK=432 +CONFIG_DRAM_ZQ=15291 +CONFIG_MMC0_CD_PIN="PE3" +CONFIG_MMC_SUNXI_SLOT_EXTRA=2 +CONFIG_USB0_ID_DET="PH8" +CONFIG_VIDEO_LCD_MODE="x:480,y:800,depth:18,pclk_khz:27500,le:12,ri:38,up:4,lo:18,hs:12,vs:8,sync:3,vmode:0" +CONFIG_VIDEO_LCD_DCLK_PHASE=0 +CONFIG_VIDEO_LCD_RESET="PL11" +CONFIG_VIDEO_LCD_BL_EN="PL6" +CONFIG_VIDEO_LCD_BL_PWM="PH0" +# CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set +# CONFIG_DISPLAY_CPUINFO is not set +# CONFIG_DISPLAY_BOARDINFO is not set +CONFIG_CMD_DFU=y +CONFIG_DFU_RAM=y +CONFIG_AXP_DCDC1_VOLT=3300 +CONFIG_USB_EHCI_HCD=y +CONFIG_USB_MUSB_GADGET=y +# CONFIG_VIDEO_DT_SIMPLEFB is not set diff --git a/br2_external/configs/mestre_x6200_defconfig b/br2_external/configs/mestre_x6200_defconfig new file mode 100644 index 0000000..302eda9 --- /dev/null +++ b/br2_external/configs/mestre_x6200_defconfig @@ -0,0 +1,127 @@ +# Mestre — Buildroot defconfig for the Xiegu X6200 +# Milestone 1: serial console + SSH + Ethernet. No GUI, no audio. +# +# Derived from gdyuldin/AetherX6200Buildroot (GPL-2.0) +# https://github.com/gdyuldin/AetherX6200Buildroot +# +# Build with: +# ./scripts/build.sh +# +# Subsequent milestones add packages incrementally on top of this base. + +# --------------------------------------------------------------------------- +# Architecture: Allwinner R16 (sun8i-a33), Cortex-A7 quad-core +# --------------------------------------------------------------------------- +BR2_arm=y +BR2_cortex_a7=y +BR2_ARM_FPU_NEON_VFPV4=y + +# --------------------------------------------------------------------------- +# Toolchain +# --------------------------------------------------------------------------- +BR2_TOOLCHAIN_BUILDROOT_CXX=y +BR2_CCACHE=y +BR2_SSP_REGULAR=y +BR2_RELRO_PARTIAL=y + +# --------------------------------------------------------------------------- +# System +# --------------------------------------------------------------------------- +BR2_TARGET_GENERIC_HOSTNAME="mestre" +BR2_TARGET_GENERIC_ISSUE="Mestre — SDR Control Head" +BR2_TARGET_GENERIC_ROOT_PASSWD="mestre" +BR2_SYSTEM_BIN_SH_BASH=y +BR2_SYSTEM_DHCP="eth0" +BR2_ROOTFS_DEVICE_CREATION_DYNAMIC_EUDEV=y +BR2_ROOTFS_OVERLAY="$(BR2_EXTERNAL_MESTRE_PATH)/board/x6200/rootfs-overlay" + +# --------------------------------------------------------------------------- +# Post-image: assemble sdcard.img via genimage +# --------------------------------------------------------------------------- +BR2_ROOTFS_POST_IMAGE_SCRIPT="support/scripts/genimage.sh" +BR2_ROOTFS_POST_SCRIPT_ARGS="-c $(BR2_EXTERNAL_MESTRE_PATH)/board/x6200/genimage.cfg" + +# --------------------------------------------------------------------------- +# Linux kernel +# --------------------------------------------------------------------------- +# Pinned to 6.6 LTS. The X6200 board support (sun8i-a33/R16) has been +# mainline since 4.x, so this is a stable, well-tested combination. +# +# NOTE: linux.config was derived from Aether's 6.1-era defconfig. +# Run `make linux-olddefconfig` after the first build to migrate any +# renamed or removed symbols for 6.6. +# +# NOTE: The LCD panel patch (patches/0001-drm-panel-jinglitai-jlt4013a.patch) +# targets 6.1-era panel/Kconfig line numbers and may need forward-porting +# for 6.6. Milestone 1 (serial console) does not require the LCD driver. +BR2_LINUX_KERNEL=y +BR2_LINUX_KERNEL_CUSTOM_VERSION=y +BR2_LINUX_KERNEL_CUSTOM_VERSION_VALUE="6.6.66" +BR2_KERNEL_HEADERS_6_6=y +BR2_LINUX_KERNEL_USE_CUSTOM_CONFIG=y +BR2_LINUX_KERNEL_CUSTOM_CONFIG_FILE="$(BR2_EXTERNAL_MESTRE_PATH)/board/x6200/linux/linux.config" +BR2_LINUX_KERNEL_CONFIG_FRAGMENT_FILES="$(BR2_EXTERNAL_MESTRE_PATH)/board/x6200/linux/linux-midi.fragment" +BR2_LINUX_KERNEL_PATCH="$(BR2_EXTERNAL_MESTRE_PATH)/board/x6200/linux/patches/" +BR2_LINUX_KERNEL_DTS_SUPPORT=y +BR2_LINUX_KERNEL_CUSTOM_DTS_PATH="$(BR2_EXTERNAL_MESTRE_PATH)/board/x6200/dts/sun8i-r16-x6200.dts" +BR2_LINUX_KERNEL_INSTALL_TARGET=y + +# --------------------------------------------------------------------------- +# U-Boot +# --------------------------------------------------------------------------- +BR2_TARGET_UBOOT=y +BR2_TARGET_UBOOT_BUILD_SYSTEM_KCONFIG=y +BR2_TARGET_UBOOT_CUSTOM_VERSION=y +BR2_TARGET_UBOOT_CUSTOM_VERSION_VALUE="2023.10" +BR2_TARGET_UBOOT_USE_CUSTOM_CONFIG=y +BR2_TARGET_UBOOT_CUSTOM_CONFIG_FILE="$(BR2_EXTERNAL_MESTRE_PATH)/board/x6200/uboot/uboot.config" +BR2_TARGET_UBOOT_NEEDS_DTC=y +BR2_TARGET_UBOOT_NEEDS_PYLIBFDT=y +BR2_TARGET_UBOOT_NEEDS_OPENSSL=y +BR2_TARGET_UBOOT_SPL=y +BR2_TARGET_UBOOT_SPL_NAME="u-boot-sunxi-with-spl.bin" +BR2_TARGET_UBOOT_CUSTOM_DTS_PATH="$(BR2_EXTERNAL_MESTRE_PATH)/board/x6200/dts/sun8i-r16-x6200.dts" + +# --------------------------------------------------------------------------- +# Root filesystem +# --------------------------------------------------------------------------- +BR2_TARGET_ROOTFS_EXT2=y +BR2_TARGET_ROOTFS_EXT2_4=y +BR2_TARGET_ROOTFS_EXT2_SIZE="512M" + +# --------------------------------------------------------------------------- +# Host tools required for image assembly +# --------------------------------------------------------------------------- +BR2_PACKAGE_HOST_DOSFSTOOLS=y +BR2_PACKAGE_HOST_GENIMAGE=y +BR2_PACKAGE_HOST_MTOOLS=y +BR2_PACKAGE_HOST_UBOOT_TOOLS=y +BR2_PACKAGE_HOST_UBOOT_TOOLS_BOOT_SCRIPT=y +BR2_PACKAGE_HOST_UBOOT_TOOLS_BOOT_SCRIPT_SOURCE="$(BR2_EXTERNAL_MESTRE_PATH)/board/x6200/uboot/boot.cmd" + +# --------------------------------------------------------------------------- +# Target packages — minimal: remote access + diagnostics +# --------------------------------------------------------------------------- +BR2_PACKAGE_OPENSSH=y +BR2_PACKAGE_NANO=y +BR2_PACKAGE_LESS=y +BR2_PACKAGE_BASH_COMPLETION=y +BR2_PACKAGE_UTIL_LINUX_BINARIES=y +BR2_PACKAGE_UTIL_LINUX_MOUNT=y +BR2_PACKAGE_UTIL_LINUX_RFKILL=y +BR2_PACKAGE_DOSFSTOOLS=y +BR2_PACKAGE_DOSFSTOOLS_MKFS_FAT=y +BR2_PACKAGE_E2FSPROGS=y +BR2_PACKAGE_I2C_TOOLS=y +BR2_PACKAGE_USBUTILS=y +BR2_PACKAGE_EVTEST=y +BR2_PACKAGE_STRACE=y + +# --------------------------------------------------------------------------- +# NOT included here (added in later milestones): +# - X11 / framebuffer console / touchscreen +# - ALSA / PulseAudio / audio stack +# - piHPSDR / WDSP / SoapySDR +# - mestred (our evdev→MIDI service) +# - Network Manager (using simple /etc/network/interfaces for now) +# --------------------------------------------------------------------------- diff --git a/br2_external/external.desc b/br2_external/external.desc new file mode 100644 index 0000000..a837013 --- /dev/null +++ b/br2_external/external.desc @@ -0,0 +1,2 @@ +name: MESTRE +desc: Open-source SDR control head for the Xiegu X6200 (Mestre project) diff --git a/br2_external/external.mk b/br2_external/external.mk new file mode 100644 index 0000000..b274be9 --- /dev/null +++ b/br2_external/external.mk @@ -0,0 +1 @@ +include $(sort $(wildcard $(BR2_EXTERNAL_MESTRE_PATH)/package/*/*.mk)) diff --git a/scripts/build.sh b/scripts/build.sh new file mode 100755 index 0000000..65db81f --- /dev/null +++ b/scripts/build.sh @@ -0,0 +1,61 @@ +#!/usr/bin/env bash +# build.sh — wrapper for Mestre Buildroot builds. +# +# Usage: +# ./scripts/build.sh # full build +# ./scripts/build.sh menuconfig # Buildroot menuconfig +# ./scripts/build.sh linux-menuconfig # Linux kernel menuconfig +# ./scripts/build.sh uboot-menuconfig # U-Boot menuconfig +# ./scripts/build.sh -rebuild # Force-rebuild a single package +# ./scripts/build.sh clean # Clean build output +# ./scripts/build.sh -- -j4 # Pass arbitrary args through to make +# +# On first invocation, the build directory is created and configured from +# the mestre_x6200_defconfig. Subsequent invocations reuse the existing +# build directory. + +set -euo pipefail + +REPO_ROOT="$(cd "$(dirname "$0")/.." && pwd)" +BUILD_DIR="$REPO_ROOT/build" +BR2_EXTERNAL="$REPO_ROOT/br2_external" +DEFCONFIG="mestre_x6200_defconfig" + +# --------------------------------------------------------------------------- +# Sanity check: submodule must be present +# --------------------------------------------------------------------------- +if [ ! -f "$REPO_ROOT/buildroot/Makefile" ]; then + echo "!!! Buildroot submodule not initialized." + echo " Run: ./scripts/setup.sh" + exit 1 +fi + +# --------------------------------------------------------------------------- +# First-time configuration +# --------------------------------------------------------------------------- +if [ ! -f "$BUILD_DIR/.config" ]; then + if [ ! -f "$BR2_EXTERNAL/configs/$DEFCONFIG" ]; then + echo "!!! Defconfig not found: $BR2_EXTERNAL/configs/$DEFCONFIG" + echo " The defconfig hasn't been added yet. See the project's" + echo " milestone status in README.md." + exit 1 + fi + + echo ">>> First-time configuration: $DEFCONFIG" + mkdir -p "$BUILD_DIR" + make -C "$REPO_ROOT/buildroot" \ + BR2_EXTERNAL="$BR2_EXTERNAL" \ + O="$BUILD_DIR" \ + "$DEFCONFIG" + echo +fi + +# --------------------------------------------------------------------------- +# Run make in the build directory +# --------------------------------------------------------------------------- +# Default to plain `make` if no extra args were passed. +if [ $# -eq 0 ]; then + make -C "$BUILD_DIR" +else + make -C "$BUILD_DIR" "$@" +fi diff --git a/scripts/setup.sh b/scripts/setup.sh new file mode 100755 index 0000000..e0cba71 --- /dev/null +++ b/scripts/setup.sh @@ -0,0 +1,59 @@ +#!/usr/bin/env bash +# setup.sh — bootstrap the Mestre development environment. +# +# Idempotent. Safe to run multiple times. +# +# Performs: +# 1. Initializes the Buildroot submodule. +# 2. Checks that the host has the tools Buildroot needs. +# +# On success, you can build with: +# ./scripts/build.sh + +set -euo pipefail + +REPO_ROOT="$(cd "$(dirname "$0")/.." && pwd)" +cd "$REPO_ROOT" + +# --------------------------------------------------------------------------- +# 1. Buildroot submodule +# --------------------------------------------------------------------------- +if [ ! -f "$REPO_ROOT/buildroot/Makefile" ]; then + echo ">>> Initializing Buildroot submodule (this may take a minute)..." + git submodule update --init buildroot +else + echo ">>> Buildroot submodule already initialized." +fi + +# --------------------------------------------------------------------------- +# 2. Host prerequisites +# --------------------------------------------------------------------------- +# Buildroot's full list lives at: +# https://buildroot.org/downloads/manual/manual.html#requirement +# We check the most commonly missing ones; Buildroot itself will surface +# anything else we've forgotten. +echo ">>> Checking host prerequisites..." +missing=() +for tool in make gcc g++ patch perl python3 cpio rsync bc unzip wget file which sed; do + if ! command -v "$tool" >/dev/null 2>&1; then + missing+=("$tool") + fi +done + +if [ ${#missing[@]} -gt 0 ]; then + echo + echo "!!! Missing host tools: ${missing[*]}" + echo + echo "On Debian/Ubuntu, install with:" + echo " sudo apt-get install build-essential patch perl python3 \\" + echo " cpio rsync bc unzip wget file" + echo + echo "See https://buildroot.org/downloads/manual/manual.html#requirement" + echo "for the complete list." + exit 1 +fi + +echo ">>> All required host tools present." +echo +echo "Setup complete. Next:" +echo " ./scripts/build.sh"