Merge branch '2021-09-02-assorted-fixes' into next

- Drop old OpenSSL support
- Add DM_HASH support, use it.
- Assorted "stemmy" platform updates
- Various bugfixes
This commit is contained in:
Tom Rini 2021-09-02 09:25:43 -04:00
commit 4bb7de1b3c
36 changed files with 2899 additions and 446 deletions

View file

@ -532,7 +532,12 @@ R: Linus Walleij <linus.walleij@linaro.org>
S: Maintained
F: arch/arm/dts/ste-*
F: arch/arm/mach-u8500/
F: drivers/gpio/nmk_gpio.c
F: drivers/phy/phy-ab8500-usb.c
F: drivers/power/pmic/ab8500.c
F: drivers/timer/nomadik-mtu-timer.c
F: drivers/usb/musb-new/ux500.c
F: drivers/video/mcde_simple.c
ARM UNIPHIER
S: Orphan (Since 2020-09)

View file

@ -1047,14 +1047,22 @@ config ARCH_U8500
select DM_GPIO
select DM_MMC if MMC
select DM_SERIAL
select DM_USB_GADGET if DM_USB
select OF_CONTROL
select SYSRESET
select TIMER
imply AB8500_USB_PHY
imply ARM_PL180_MMCI
imply CLK
imply DM_PMIC
imply DM_RTC
imply NOMADIK_GPIO
imply NOMADIK_MTU_TIMER
imply PHY
imply PL01X_SERIAL
imply PMIC_AB8500
imply RTC_PL031
imply SYS_THUMB_BUILD
imply SYSRESET_SYSCON
config ARCH_VERSAL

View file

@ -42,15 +42,15 @@
ab8500-rtc {
compatible = "stericsson,ab8500-rtc";
interrupts = <17 IRQ_TYPE_LEVEL_HIGH
18 IRQ_TYPE_LEVEL_HIGH>;
interrupts = <17 IRQ_TYPE_LEVEL_HIGH>,
<18 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "60S", "ALARM";
};
gpadc: ab8500-gpadc {
compatible = "stericsson,ab8500-gpadc";
interrupts = <32 IRQ_TYPE_LEVEL_HIGH
39 IRQ_TYPE_LEVEL_HIGH>;
interrupts = <32 IRQ_TYPE_LEVEL_HIGH>,
<39 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "HW_CONV_END", "SW_CONV_END";
vddadc-supply = <&ab8500_ldo_tvout_reg>;
#address-cells = <1>;
@ -122,9 +122,11 @@
ab8500_temp {
compatible = "stericsson,abx500-temp";
interrupts = <3 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "ABX500_TEMP_WARM";
io-channels = <&gpadc 0x06>,
<&gpadc 0x07>;
io-channel-name = "aux1", "aux2";
io-channel-names = "aux1", "aux2";
};
ab8500_battery: ab8500_battery {
@ -134,29 +136,77 @@
ab8500_fg {
compatible = "stericsson,ab8500-fg";
battery = <&ab8500_battery>;
interrupts = <24 IRQ_TYPE_LEVEL_HIGH>,
<8 IRQ_TYPE_LEVEL_HIGH>,
<28 IRQ_TYPE_LEVEL_HIGH>,
<27 IRQ_TYPE_LEVEL_HIGH>,
<26 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "NCONV_ACCU",
"BATT_OVV",
"LOW_BAT_F",
"CC_INT_CALIB",
"CCEOC";
battery = <&ab8500_battery>;
io-channels = <&gpadc 0x08>;
io-channel-name = "main_bat_v";
io-channel-names = "main_bat_v";
};
ab8500_btemp {
compatible = "stericsson,ab8500-btemp";
battery = <&ab8500_battery>;
interrupts = <20 IRQ_TYPE_LEVEL_HIGH>,
<80 IRQ_TYPE_LEVEL_HIGH>,
<83 IRQ_TYPE_LEVEL_HIGH>,
<81 IRQ_TYPE_LEVEL_HIGH>,
<82 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "BAT_CTRL_INDB",
"BTEMP_LOW",
"BTEMP_HIGH",
"BTEMP_LOW_MEDIUM",
"BTEMP_MEDIUM_HIGH";
battery = <&ab8500_battery>;
io-channels = <&gpadc 0x02>,
<&gpadc 0x01>;
io-channel-name = "btemp_ball",
io-channel-names = "btemp_ball",
"bat_ctrl";
};
ab8500_charger {
compatible = "stericsson,ab8500-charger";
compatible = "stericsson,ab8500-charger";
interrupts = <10 IRQ_TYPE_LEVEL_HIGH>,
<11 IRQ_TYPE_LEVEL_HIGH>,
<0 IRQ_TYPE_LEVEL_HIGH>,
<107 IRQ_TYPE_LEVEL_HIGH>,
<106 IRQ_TYPE_LEVEL_HIGH>,
<14 IRQ_TYPE_LEVEL_HIGH>,
<15 IRQ_TYPE_LEVEL_HIGH>,
<79 IRQ_TYPE_LEVEL_HIGH>,
<105 IRQ_TYPE_LEVEL_HIGH>,
<104 IRQ_TYPE_LEVEL_HIGH>,
<89 IRQ_TYPE_LEVEL_HIGH>,
<22 IRQ_TYPE_LEVEL_HIGH>,
<21 IRQ_TYPE_LEVEL_HIGH>,
<16 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "MAIN_CH_UNPLUG_DET",
"MAIN_CHARGE_PLUG_DET",
"MAIN_EXT_CH_NOT_OK",
"MAIN_CH_TH_PROT_R",
"MAIN_CH_TH_PROT_F",
"VBUS_DET_F",
"VBUS_DET_R",
"USB_LINK_STATUS",
"USB_CH_TH_PROT_R",
"USB_CH_TH_PROT_F",
"USB_CHARGER_NOT_OKR",
"VBUS_OVV",
"CH_WD_EXP",
"VBUS_CH_DROP_END";
battery = <&ab8500_battery>;
vddadc-supply = <&ab8500_ldo_tvout_reg>;
io-channels = <&gpadc 0x03>,
<&gpadc 0x0a>,
<&gpadc 0x09>,
<&gpadc 0x0b>;
io-channel-name = "main_charger_v",
io-channel-names = "main_charger_v",
"main_charger_c",
"vbus_v",
"usb_charger_c";
@ -167,15 +217,15 @@
battery = <&ab8500_battery>;
};
ab8500_usb {
ab8500_usb: ab8500_usb {
compatible = "stericsson,ab8500-usb";
interrupts = < 90 IRQ_TYPE_LEVEL_HIGH
96 IRQ_TYPE_LEVEL_HIGH
14 IRQ_TYPE_LEVEL_HIGH
15 IRQ_TYPE_LEVEL_HIGH
79 IRQ_TYPE_LEVEL_HIGH
74 IRQ_TYPE_LEVEL_HIGH
75 IRQ_TYPE_LEVEL_HIGH>;
interrupts = <90 IRQ_TYPE_LEVEL_HIGH>,
<96 IRQ_TYPE_LEVEL_HIGH>,
<14 IRQ_TYPE_LEVEL_HIGH>,
<15 IRQ_TYPE_LEVEL_HIGH>,
<79 IRQ_TYPE_LEVEL_HIGH>,
<74 IRQ_TYPE_LEVEL_HIGH>,
<75 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "ID_WAKEUP_R",
"ID_WAKEUP_F",
"VBUS_DET_F",
@ -188,12 +238,13 @@
musb_1v8-supply = <&db8500_vsmps2_reg>;
clocks = <&prcmu_clk PRCMU_SYSCLK>;
clock-names = "sysclk";
#phy-cells = <0>;
};
ab8500-ponkey {
compatible = "stericsson,ab8500-poweron-key";
interrupts = <6 IRQ_TYPE_LEVEL_HIGH
7 IRQ_TYPE_LEVEL_HIGH>;
interrupts = <6 IRQ_TYPE_LEVEL_HIGH>,
<7 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "ONKEY_DBF", "ONKEY_DBR";
};
@ -201,7 +252,19 @@
compatible = "stericsson,ab8500-sysctrl";
};
ab8500-pwm {
ab8500-pwm-1 {
compatible = "stericsson,ab8500-pwm";
clocks = <&ab8500_clock AB8500_SYSCLK_INT>;
clock-names = "intclk";
};
ab8500-pwm-2 {
compatible = "stericsson,ab8500-pwm";
clocks = <&ab8500_clock AB8500_SYSCLK_INT>;
clock-names = "intclk";
};
ab8500-pwm-3 {
compatible = "stericsson,ab8500-pwm";
clocks = <&ab8500_clock AB8500_SYSCLK_INT>;
clock-names = "intclk";
@ -255,8 +318,8 @@
// supplies to the display/camera
ab8500_ldo_aux1_reg: ab8500_ldo_aux1 {
regulator-min-microvolt = <2500000>;
regulator-max-microvolt = <2900000>;
regulator-min-microvolt = <2800000>;
regulator-max-microvolt = <3300000>;
regulator-boot-on;
/* BUG: If turned off MMC will be affected. */
regulator-always-on;
@ -324,5 +387,10 @@
vana-supply = <&ab8500_ldo_ana_reg>;
};
};
usb_per5@a03e0000 {
phys = <&ab8500_usb>;
phy-names = "usb";
};
};
};

View file

@ -13,7 +13,8 @@
<&gpadc 0x08>, /* Main battery voltage */
<&gpadc 0x09>, /* VBUS */
<&gpadc 0x0b>, /* Charger current */
<&gpadc 0x0c>; /* Backup battery voltage */
<&gpadc 0x0c>, /* Backup battery voltage */
<&gpadc 0x0d>; /* Die temperature */
};
soc {
@ -38,16 +39,15 @@
ab8500-rtc {
compatible = "stericsson,ab8500-rtc";
interrupts = <17 IRQ_TYPE_LEVEL_HIGH
18 IRQ_TYPE_LEVEL_HIGH>;
interrupts = <17 IRQ_TYPE_LEVEL_HIGH>,
<18 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "60S", "ALARM";
};
gpadc: ab8500-gpadc {
compatible = "stericsson,ab8500-gpadc";
interrupts = <32 IRQ_TYPE_LEVEL_HIGH
39 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "HW_CONV_END", "SW_CONV_END";
interrupts = <39 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "SW_CONV_END";
vddadc-supply = <&ab8500_ldo_adc_reg>;
#address-cells = <1>;
#size-cells = <0>;
@ -84,42 +84,93 @@
bk_bat_v: channel@0c {
reg = <0x0c>;
};
die_temp: channel@0d {
reg = <0x0d>;
};
usb_id: channel@0e {
reg = <0x0e>;
};
};
ab8500_battery: ab8500_battery {
status = "disabled";
stericsson,battery-type = "LIPO";
thermistor-on-batctrl;
};
ab8500_fg {
status = "disabled";
compatible = "stericsson,ab8500-fg";
interrupts = <24 IRQ_TYPE_LEVEL_HIGH>,
<8 IRQ_TYPE_LEVEL_HIGH>,
<28 IRQ_TYPE_LEVEL_HIGH>,
<27 IRQ_TYPE_LEVEL_HIGH>,
<26 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "NCONV_ACCU",
"BATT_OVV",
"LOW_BAT_F",
"CC_INT_CALIB",
"CCEOC";
battery = <&ab8500_battery>;
io-channels = <&gpadc 0x08>;
io-channel-name = "main_bat_v";
io-channel-names = "main_bat_v";
};
ab8500_btemp {
status = "disabled";
compatible = "stericsson,ab8500-btemp";
interrupts = <20 IRQ_TYPE_LEVEL_HIGH>,
<80 IRQ_TYPE_LEVEL_HIGH>,
<83 IRQ_TYPE_LEVEL_HIGH>,
<81 IRQ_TYPE_LEVEL_HIGH>,
<82 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "BAT_CTRL_INDB",
"BTEMP_LOW",
"BTEMP_HIGH",
"BTEMP_LOW_MEDIUM",
"BTEMP_MEDIUM_HIGH";
battery = <&ab8500_battery>;
io-channels = <&gpadc 0x02>,
<&gpadc 0x01>;
io-channel-name = "btemp_ball",
io-channel-names = "btemp_ball",
"bat_ctrl";
};
ab8500_charger {
status = "disabled";
compatible = "stericsson,ab8500-charger";
interrupts = <10 IRQ_TYPE_LEVEL_HIGH>,
<11 IRQ_TYPE_LEVEL_HIGH>,
<0 IRQ_TYPE_LEVEL_HIGH>,
<107 IRQ_TYPE_LEVEL_HIGH>,
<106 IRQ_TYPE_LEVEL_HIGH>,
<14 IRQ_TYPE_LEVEL_HIGH>,
<15 IRQ_TYPE_LEVEL_HIGH>,
<79 IRQ_TYPE_LEVEL_HIGH>,
<105 IRQ_TYPE_LEVEL_HIGH>,
<104 IRQ_TYPE_LEVEL_HIGH>,
<89 IRQ_TYPE_LEVEL_HIGH>,
<22 IRQ_TYPE_LEVEL_HIGH>,
<21 IRQ_TYPE_LEVEL_HIGH>,
<16 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "MAIN_CH_UNPLUG_DET",
"MAIN_CHARGE_PLUG_DET",
"MAIN_EXT_CH_NOT_OK",
"MAIN_CH_TH_PROT_R",
"MAIN_CH_TH_PROT_F",
"VBUS_DET_F",
"VBUS_DET_R",
"USB_LINK_STATUS",
"USB_CH_TH_PROT_R",
"USB_CH_TH_PROT_F",
"USB_CHARGER_NOT_OKR",
"VBUS_OVV",
"CH_WD_EXP",
"VBUS_CH_DROP_END";
battery = <&ab8500_battery>;
vddadc-supply = <&ab8500_ldo_adc_reg>;
io-channels = <&gpadc 0x09>,
<&gpadc 0x0b>;
io-channel-name = "vbus_v",
io-channel-names = "vbus_v",
"usb_charger_c";
};
@ -131,13 +182,13 @@
ab8500_usb: ab8500_usb {
compatible = "stericsson,ab8500-usb";
interrupts = < 90 IRQ_TYPE_LEVEL_HIGH
96 IRQ_TYPE_LEVEL_HIGH
14 IRQ_TYPE_LEVEL_HIGH
15 IRQ_TYPE_LEVEL_HIGH
79 IRQ_TYPE_LEVEL_HIGH
74 IRQ_TYPE_LEVEL_HIGH
75 IRQ_TYPE_LEVEL_HIGH>;
interrupts = <90 IRQ_TYPE_LEVEL_HIGH>,
<96 IRQ_TYPE_LEVEL_HIGH>,
<14 IRQ_TYPE_LEVEL_HIGH>,
<15 IRQ_TYPE_LEVEL_HIGH>,
<79 IRQ_TYPE_LEVEL_HIGH>,
<74 IRQ_TYPE_LEVEL_HIGH>,
<75 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "ID_WAKEUP_R",
"ID_WAKEUP_F",
"VBUS_DET_F",
@ -150,12 +201,13 @@
musb_1v8-supply = <&db8500_vsmps2_reg>;
clocks = <&prcmu_clk PRCMU_SYSCLK>;
clock-names = "sysclk";
#phy-cells = <0>;
};
ab8500-ponkey {
compatible = "stericsson,ab8500-poweron-key";
interrupts = <6 IRQ_TYPE_LEVEL_HIGH
7 IRQ_TYPE_LEVEL_HIGH>;
interrupts = <6 IRQ_TYPE_LEVEL_HIGH>,
<7 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "ONKEY_DBF", "ONKEY_DBR";
};
@ -271,5 +323,10 @@
vana-supply = <&ab8500_ldo_ana_reg>;
};
};
usb_per5@a03e0000 {
phys = <&ab8500_usb>;
phy-names = "usb";
};
};
};

View file

@ -4,8 +4,14 @@
#include "ste-dbx5x0.dtsi"
/ {
/* FIXME: Remove this when clk driver is implemented */
sdmmcclk: sdmmcclk {
compatible = "fixed-clock";
#clock-cells = <0>;
clock-frequency = <100000000>;
};
soc {
/* FIXME: Remove this when clk driver is implemented */
mtu@a03c6000 {
clock-frequency = <133000000>;
};
@ -18,6 +24,9 @@
uart@80007000 {
clock = <38400000>;
};
mmc@80005000 {
clocks = <&sdmmcclk>;
};
};
reboot {

View file

@ -260,7 +260,7 @@
reg = <0x80150000 0x2000>;
};
L2: l2-cache {
L2: cache-controller {
compatible = "arm,pl310-cache";
reg = <0xa0412000 0x1000>;
interrupts = <GIC_SPI 13 IRQ_TYPE_LEVEL_HIGH>;
@ -883,7 +883,7 @@
status = "disabled";
};
sdi0_per1@80126000 {
mmc@80126000 {
compatible = "arm,pl18x", "arm,primecell";
reg = <0x80126000 0x1000>;
interrupts = <GIC_SPI 60 IRQ_TYPE_LEVEL_HIGH>;
@ -899,7 +899,7 @@
status = "disabled";
};
sdi1_per2@80118000 {
mmc@80118000 {
compatible = "arm,pl18x", "arm,primecell";
reg = <0x80118000 0x1000>;
interrupts = <GIC_SPI 50 IRQ_TYPE_LEVEL_HIGH>;
@ -915,7 +915,7 @@
status = "disabled";
};
sdi2_per3@80005000 {
mmc@80005000 {
compatible = "arm,pl18x", "arm,primecell";
reg = <0x80005000 0x1000>;
interrupts = <GIC_SPI 41 IRQ_TYPE_LEVEL_HIGH>;
@ -931,7 +931,7 @@
status = "disabled";
};
sdi3_per2@80119000 {
mmc@80119000 {
compatible = "arm,pl18x", "arm,primecell";
reg = <0x80119000 0x1000>;
interrupts = <GIC_SPI 59 IRQ_TYPE_LEVEL_HIGH>;
@ -947,7 +947,7 @@
status = "disabled";
};
sdi4_per2@80114000 {
mmc@80114000 {
compatible = "arm,pl18x", "arm,primecell";
reg = <0x80114000 0x1000>;
interrupts = <GIC_SPI 99 IRQ_TYPE_LEVEL_HIGH>;
@ -963,7 +963,7 @@
status = "disabled";
};
sdi5_per3@80008000 {
mmc@80008000 {
compatible = "arm,pl18x", "arm,primecell";
reg = <0x80008000 0x1000>;
interrupts = <GIC_SPI 100 IRQ_TYPE_LEVEL_HIGH>;

View file

@ -12,9 +12,25 @@
};
soc {
/* eMMC */
mmc@80005000 {
status = "okay";
arm,primecell-periphid = <0x10480180>;
max-frequency = <100000000>;
bus-width = <8>;
non-removable;
cap-mmc-highspeed;
};
/* Debugging console UART */
uart@80007000 {
status = "okay";
};
mcde@a0350000 {
status = "okay";
};
};
};

View file

@ -13,14 +13,15 @@ config TARGET_STEMMY
The Samsung "stemmy" board supports Samsung smartphones released with
the ST-Ericsson NovaThor U8500 SoC, e.g.
- Samsung Galaxy S III mini (GT-I8190) "golden"
- Samsung Galaxy S Advance (GT-I9070) "janice"
- Samsung Galaxy Xcover 2 (GT-S7710) "skomer"
- Samsung Galaxy Ace 2 (GT-I8160) "codina"
- Samsung Galaxy Amp (SGH-I407) "kyle"
- Samsung Galaxy Beam (GT-I8530) "gavini"
- Samsung Galaxy Exhibit (SGH-T599) "codina" (TMO)
- Samsung Galaxy S Advance (GT-I9070) "janice"
- Samsung Galaxy S III mini (GT-I8190) "golden"
- Samsung Galaxy Xcover 2 (GT-S7710) "skomer"
and likely others as well (untested).
See board/ste/stemmy/README for details.
See doc/board/ste/stemmy.rst for details.
endchoice

View file

@ -2,5 +2,6 @@ STEMMY BOARD
M: Stephan Gerhold <stephan@gerhold.net>
S: Maintained
F: board/ste/stemmy/
F: include/configs/stemmy.h
F: configs/stemmy_defconfig
F: doc/board/ste/stemmy.rst
F: include/configs/stemmy.h

View file

@ -1,50 +0,0 @@
ST-Ericsson U8500 Samsung "stemmy" board
========================================
The "stemmy" board supports Samsung smartphones released with
the ST-Ericsson NovaThor U8500 SoC, e.g.
- Samsung Galaxy S III mini (GT-I8190) "golden"
- Samsung Galaxy S Advance (GT-I9070) "janice"
- Samsung Galaxy Xcover 2 (GT-S7710) "skomer"
- Samsung Galaxy Ace 2 (GT-I8160) "codina"
and likely others as well (untested).
At the moment, U-Boot is intended to be chain-loaded from
the original Samsung bootloader, not replacing it entirely.
Installation
------------
1. Setup cross compiler, e.g. export CROSS_COMPILE=arm-none-eabi-
2. make stemmy_defconfig
3. make
For newer devices (golden and skomer), the U-Boot binary has to be packed into
an Android boot image. janice boots the raw U-Boot binary from the boot partition.
4. Obtain mkbootimg, e.g. https://android.googlesource.com/platform/system/core/+/refs/tags/android-7.1.2_r37/mkbootimg/mkbootimg
5. mkbootimg \
--kernel=u-boot.bin \
--base=0x00000000 \
--kernel_offset=0x00100000 \
--ramdisk_offset=0x02000000 \
--tags_offset=0x00000100 \
--output=u-boot.img
6. Enter Samsung download mode (press Power + Home + Volume Down)
7. Flash U-Boot image to Android boot partition using Heimdall:
https://gitlab.com/BenjaminDobell/Heimdall
heimdall flash --Kernel u-boot.(bin|img)
8. After reboot U-Boot prompt should appear via UART.
UART
----
UART is available through the micro USB port, similar to the Carkit standard.
With a ~619kOhm resistor between ID and GND, 1.8V RX/TX is available at D+/D-.
Make sure to connect the UART cable *before* turning on the phone.

View file

@ -535,6 +535,9 @@ static ulong load_serial_bin(ulong offset)
udelay(1000);
}
if (size == 0)
return ~0; /* Download aborted */
flush_cache(offset, size);
printf("## Total Size = 0x%08x = %d Bytes\n", size, size);

View file

@ -25,6 +25,10 @@
#include <asm/io.h>
#include <malloc.h>
#include <asm/global_data.h>
#ifdef CONFIG_DM_HASH
#include <dm.h>
#include <u-boot/hash.h>
#endif
DECLARE_GLOBAL_DATA_PTR;
#endif /* !USE_HOSTCC*/
@ -1214,6 +1218,31 @@ int fit_set_timestamp(void *fit, int noffset, time_t timestamp)
int calculate_hash(const void *data, int data_len, const char *algo,
uint8_t *value, int *value_len)
{
#if !defined(USE_HOSTCC) && defined(CONFIG_DM_HASH)
int rc;
enum HASH_ALGO hash_algo;
struct udevice *dev;
rc = uclass_get_device(UCLASS_HASH, 0, &dev);
if (rc) {
debug("failed to get hash device, rc=%d\n", rc);
return -1;
}
hash_algo = hash_algo_lookup_by_name(algo);
if (hash_algo == HASH_ALGO_INVALID) {
debug("Unsupported hash algorithm\n");
return -1;
};
rc = hash_digest_wd(dev, hash_algo, data, data_len, value, CHUNKSZ);
if (rc) {
debug("failed to get hash value, rc=%d\n", rc);
return -1;
}
*value_len = hash_algo_digest_size(hash_algo);
#else
if (IMAGE_ENABLE_CRC32 && strcmp(algo, "crc32") == 0) {
*((uint32_t *)value) = crc32_wd(0, data, data_len,
CHUNKSZ_CRC32);
@ -1242,6 +1271,7 @@ int calculate_hash(const void *data, int data_len, const char *algo,
debug("Unsupported hash alogrithm\n");
return -1;
}
#endif
return 0;
}

View file

@ -6,6 +6,8 @@ CONFIG_NR_DRAM_BANKS=2
CONFIG_SYS_MALLOC_LEN=0x0200000
CONFIG_DEFAULT_DEVICE_TREE="ste-ux500-samsung-stemmy"
CONFIG_SYS_LOAD_ADDR=0x100000
CONFIG_USE_BOOTCOMMAND=y
CONFIG_BOOTCOMMAND="run fastbootcmd"
CONFIG_SYS_CONSOLE_INFO_QUIET=y
CONFIG_HUSH_PARSER=y
CONFIG_CMD_CONFIG=y
@ -17,5 +19,17 @@ CONFIG_CMD_PART=y
CONFIG_CMD_GETTIME=y
CONFIG_EFI_PARTITION=y
# CONFIG_NET is not set
CONFIG_USB_FUNCTION_FASTBOOT=y
CONFIG_FASTBOOT_BUF_ADDR=0x18100000
CONFIG_FASTBOOT_FLASH=y
CONFIG_FASTBOOT_FLASH_MMC_DEV=0
# CONFIG_MMC_HW_PARTITIONING is not set
CONFIG_USB=y
CONFIG_USB_MUSB_GADGET=y
CONFIG_USB_GADGET=y
CONFIG_USB_GADGET_VENDOR_NUM=0x04e8
CONFIG_USB_GADGET_PRODUCT_NUM=0x685d
CONFIG_DM_VIDEO=y
CONFIG_SYS_WHITE_ON_BLACK=y
CONFIG_VIDEO_MCDE_SIMPLE=y
# CONFIG_EFI_LOADER is not set

View file

@ -26,6 +26,7 @@ Board-specific doc
sipeed/index
socionext/index
st/index
ste/index
tbs/index
ti/index
toradex/index

9
doc/board/ste/index.rst Normal file
View file

@ -0,0 +1,9 @@
.. SPDX-License-Identifier: GPL-2.0+
ST-Ericsson
===========
.. toctree::
:maxdepth: 2
stemmy

81
doc/board/ste/stemmy.rst Normal file
View file

@ -0,0 +1,81 @@
.. SPDX-License-Identifier: GPL-2.0+
.. sectionauthor:: Stephan Gerhold <stephan@gerhold.net>
ST-Ericsson U8500 Samsung "stemmy" board
========================================
The "stemmy" board supports Samsung smartphones released with
the ST-Ericsson NovaThor U8500 SoC, e.g.
+---------------------------+----------+--------------+----------------+
| Device | Model | Codename | U-Boot |
+===========================+==========+==============+================+
| Samsung Galaxy Ace 2 | GT-I8160 | codina | ``u-boot.bin`` |
+---------------------------+----------+--------------+----------------+
| Samsung Galaxy Amp | SGH-I407 | kyle | ``u-boot.img`` |
+---------------------------+----------+--------------+----------------+
| Samsung Galaxy Beam | GT-I8530 | gavini | ``u-boot.bin`` |
+---------------------------+----------+--------------+----------------+
| Samsung Galaxy Exhibit | SGH-T599 | codina (TMO) | ``u-boot.bin`` |
+---------------------------+----------+--------------+----------------+
| Samsung Galaxy S Advance | GT-I9070 | janice | ``u-boot.bin`` |
+---------------------------+----------+--------------+----------------+
| Samsung Galaxy S III mini | GT-I8190 | golden | ``u-boot.img`` |
+---------------------------+----------+--------------+----------------+
| Samsung Galaxy Xcover 2 | GT-S7710 | skomer | ``u-boot.img`` |
+---------------------------+----------+--------------+----------------+
At the moment, U-Boot is intended to be chain-loaded from
the original Samsung bootloader, not replacing it entirely.
Installation
------------
First, setup ``CROSS_COMPILE`` for ARMv7. Then, build U-Boot for ``stemmy``::
$ export CROSS_COMPILE=arm-none-eabi-
$ make stemmy_defconfig
$ make
This will build ``u-boot.bin`` in the configured output directory.
For newer devices (check ``u-boot.img`` in the table above), the U-Boot binary
has to be packed into an Android boot image. Devices with ``u-boot.bin`` boot
the raw U-Boot binary from the boot partition. You can build the Android boot
image with ``mkbootimg``, e.g. from from android-7.1.2_r37_::
$ mkbootimg \
--kernel=u-boot.bin \
--base=0x00000000 \
--kernel_offset=0x00100000 \
--ramdisk_offset=0x02000000 \
--tags_offset=0x00000100 \
--output=u-boot.img
.. _android-7.1.2_r37: https://android.googlesource.com/platform/system/core/+/refs/tags/android-7.1.2_r37/mkbootimg/mkbootimg
To flash the U-Boot binary, enter the Samsung download mode
(press Power + Home + Volume Down). Use Heimdall_ to flash the U-Boot image to
the Android boot partition::
$ heimdall flash --Kernel u-boot.(bin|img)
If this is not working but there are messages like ``Android recovery image`` in
the UART console, you can try flashing to the recovery partition instead::
$ heimdall flash --Kernel2 u-boot.(bin|img)
.. _Heimdall: https://gitlab.com/BenjaminDobell/Heimdall
After a reboot the U-Boot prompt should appear via UART. Unless interrupted it
automatically boots to USB Fastboot mode where Android boot images can be booted
via ``fastboot boot boot.img``. It is mainly intended to boot mainline Linux,
but booting original Samsung Android boot images is also supported (e.g. for
charging).
UART
----
UART is available through the micro USB port, similar to the Carkit standard.
With a ~619kOhm resistor between ID and GND, 1.8V RX/TX is available at D+/D-.
.. note::
Make sure to connect the UART cable **before** turning on the phone.

755
doc/develop/checkpatch.rst Normal file
View file

@ -0,0 +1,755 @@
.. SPDX-License-Identifier: GPL-2.0-only
==========
Checkpatch
==========
Checkpatch (scripts/checkpatch.pl) is a perl script which checks for trivial
style violations in patches and optionally corrects them. Checkpatch can
also be run on file contexts and without the kernel tree.
Checkpatch is not always right. Your judgement takes precedence over checkpatch
messages. If your code looks better with the violations, then its probably
best left alone.
Options
=======
This section will describe the options checkpatch can be run with.
Usage::
./scripts/checkpatch.pl [OPTION]... [FILE]...
Available options:
- -q, --quiet
Enable quiet mode.
- -v, --verbose
Enable verbose mode. Additional verbose test descriptions are output
so as to provide information on why that particular message is shown.
- --no-tree
Run checkpatch without the kernel tree.
- --no-signoff
Disable the 'Signed-off-by' line check. The sign-off is a simple line at
the end of the explanation for the patch, which certifies that you wrote it
or otherwise have the right to pass it on as an open-source patch.
Example::
Signed-off-by: Random J Developer <random@developer.example.org>
Setting this flag effectively stops a message for a missing signed-off-by
line in a patch context.
- --patch
Treat FILE as a patch. This is the default option and need not be
explicitly specified.
- --emacs
Set output to emacs compile window format. This allows emacs users to jump
from the error in the compile window directly to the offending line in the
patch.
- --terse
Output only one line per report.
- --showfile
Show the diffed file position instead of the input file position.
- -g, --git
Treat FILE as a single commit or a git revision range.
Single commit with:
- <rev>
- <rev>^
- <rev>~n
Multiple commits with:
- <rev1>..<rev2>
- <rev1>...<rev2>
- <rev>-<count>
- -f, --file
Treat FILE as a regular source file. This option must be used when running
checkpatch on source files in the kernel.
- --subjective, --strict
Enable stricter tests in checkpatch. By default the tests emitted as CHECK
do not activate by default. Use this flag to activate the CHECK tests.
- --list-types
Every message emitted by checkpatch has an associated TYPE. Add this flag
to display all the types in checkpatch.
Note that when this flag is active, checkpatch does not read the input FILE,
and no message is emitted. Only a list of types in checkpatch is output.
- --types TYPE(,TYPE2...)
Only display messages with the given types.
Example::
./scripts/checkpatch.pl mypatch.patch --types EMAIL_SUBJECT,BRACES
- --ignore TYPE(,TYPE2...)
Checkpatch will not emit messages for the specified types.
Example::
./scripts/checkpatch.pl mypatch.patch --ignore EMAIL_SUBJECT,BRACES
- --show-types
By default checkpatch doesn't display the type associated with the messages.
Set this flag to show the message type in the output.
- --max-line-length=n
Set the max line length (default 100). If a line exceeds the specified
length, a LONG_LINE message is emitted.
The message level is different for patch and file contexts. For patches,
a WARNING is emitted. While a milder CHECK is emitted for files. So for
file contexts, the --strict flag must also be enabled.
- --min-conf-desc-length=n
Set the Kconfig entry minimum description length, if shorter, warn.
- --tab-size=n
Set the number of spaces for tab (default 8).
- --root=PATH
PATH to the kernel tree root.
This option must be specified when invoking checkpatch from outside
the kernel root.
- --no-summary
Suppress the per file summary.
- --mailback
Only produce a report in case of Warnings or Errors. Milder Checks are
excluded from this.
- --summary-file
Include the filename in summary.
- --debug KEY=[0|1]
Turn on/off debugging of KEY, where KEY is one of 'values', 'possible',
'type', and 'attr' (default is all off).
- --fix
This is an EXPERIMENTAL feature. If correctable errors exists, a file
<inputfile>.EXPERIMENTAL-checkpatch-fixes is created which has the
automatically fixable errors corrected.
- --fix-inplace
EXPERIMENTAL - Similar to --fix but input file is overwritten with fixes.
DO NOT USE this flag unless you are absolutely sure and you have a backup
in place.
- --ignore-perl-version
Override checking of perl version. Runtime errors maybe encountered after
enabling this flag if the perl version does not meet the minimum specified.
- --codespell
Use the codespell dictionary for checking spelling errors.
- --codespellfile
Use the specified codespell file.
Default is '/usr/share/codespell/dictionary.txt'.
- --typedefsfile
Read additional types from this file.
- --color[=WHEN]
Use colors 'always', 'never', or only when output is a terminal ('auto').
Default is 'auto'.
- --kconfig-prefix=WORD
Use WORD as a prefix for Kconfig symbols (default is `CONFIG_`).
- -h, --help, --version
Display the help text.
Message Levels
==============
Messages in checkpatch are divided into three levels. The levels of messages
in checkpatch denote the severity of the error. They are:
- ERROR
This is the most strict level. Messages of type ERROR must be taken
seriously as they denote things that are very likely to be wrong.
- WARNING
This is the next stricter level. Messages of type WARNING requires a
more careful review. But it is milder than an ERROR.
- CHECK
This is the mildest level. These are things which may require some thought.
Type Descriptions
=================
This section contains a description of all the message types in checkpatch.
.. Types in this section are also parsed by checkpatch.
.. The types are grouped into subsections based on use.
Allocation style
----------------
**ALLOC_ARRAY_ARGS**
The first argument for kcalloc or kmalloc_array should be the
number of elements. sizeof() as the first argument is generally
wrong.
See: https://www.kernel.org/doc/html/latest/core-api/memory-allocation.html
**ALLOC_SIZEOF_STRUCT**
The allocation style is bad. In general for family of
allocation functions using sizeof() to get memory size,
constructs like::
p = alloc(sizeof(struct foo), ...)
should be::
p = alloc(sizeof(*p), ...)
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#allocating-memory
**ALLOC_WITH_MULTIPLY**
Prefer kmalloc_array/kcalloc over kmalloc/kzalloc with a
sizeof multiply.
See: https://www.kernel.org/doc/html/latest/core-api/memory-allocation.html
API usage
---------
**ARCH_DEFINES**
Architecture specific defines should be avoided wherever
possible.
**ARCH_INCLUDE_LINUX**
Whenever asm/file.h is included and linux/file.h exists, a
conversion can be made when linux/file.h includes asm/file.h.
However this is not always the case (See signal.h).
This message type is emitted only for includes from arch/.
**AVOID_BUG**
BUG() or BUG_ON() should be avoided totally.
Use WARN() and WARN_ON() instead, and handle the "impossible"
error condition as gracefully as possible.
See: https://www.kernel.org/doc/html/latest/process/deprecated.html#bug-and-bug-on
**CONSIDER_KSTRTO**
The simple_strtol(), simple_strtoll(), simple_strtoul(), and
simple_strtoull() functions explicitly ignore overflows, which
may lead to unexpected results in callers. The respective kstrtol(),
kstrtoll(), kstrtoul(), and kstrtoull() functions tend to be the
correct replacements.
See: https://www.kernel.org/doc/html/latest/process/deprecated.html#simple-strtol-simple-strtoll-simple-strtoul-simple-strtoull
**LOCKDEP**
The lockdep_no_validate class was added as a temporary measure to
prevent warnings on conversion of device->sem to device->mutex.
It should not be used for any other purpose.
See: https://lore.kernel.org/lkml/1268959062.9440.467.camel@laptop/
**MALFORMED_INCLUDE**
The #include statement has a malformed path. This has happened
because the author has included a double slash "//" in the pathname
accidentally.
**USE_LOCKDEP**
lockdep_assert_held() annotations should be preferred over
assertions based on spin_is_locked()
See: https://www.kernel.org/doc/html/latest/locking/lockdep-design.html#annotations
**UAPI_INCLUDE**
No #include statements in include/uapi should use a uapi/ path.
Comment style
-------------
**BLOCK_COMMENT_STYLE**
The comment style is incorrect. The preferred style for multi-
line comments is::
/*
* This is the preferred style
* for multi line comments.
*/
The networking comment style is a bit different, with the first line
not empty like the former::
/* This is the preferred comment style
* for files in net/ and drivers/net/
*/
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#commenting
**C99_COMMENTS**
C99 style single line comments (//) should not be used.
Prefer the block comment style instead.
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#commenting
Commit message
--------------
**BAD_SIGN_OFF**
The signed-off-by line does not fall in line with the standards
specified by the community.
See: https://www.kernel.org/doc/html/latest/process/submitting-patches.html#developer-s-certificate-of-origin-1-1
**BAD_STABLE_ADDRESS_STYLE**
The email format for stable is incorrect.
Some valid options for stable address are::
1. stable@vger.kernel.org
2. stable@kernel.org
For adding version info, the following comment style should be used::
stable@vger.kernel.org # version info
**COMMIT_COMMENT_SYMBOL**
Commit log lines starting with a '#' are ignored by git as
comments. To solve this problem addition of a single space
infront of the log line is enough.
**COMMIT_MESSAGE**
The patch is missing a commit description. A brief
description of the changes made by the patch should be added.
See: https://www.kernel.org/doc/html/latest/process/submitting-patches.html#describe-your-changes
**MISSING_SIGN_OFF**
The patch is missing a Signed-off-by line. A signed-off-by
line should be added according to Developer's certificate of
Origin.
See: https://www.kernel.org/doc/html/latest/process/submitting-patches.html#sign-your-work-the-developer-s-certificate-of-origin
**NO_AUTHOR_SIGN_OFF**
The author of the patch has not signed off the patch. It is
required that a simple sign off line should be present at the
end of explanation of the patch to denote that the author has
written it or otherwise has the rights to pass it on as an open
source patch.
See: https://www.kernel.org/doc/html/latest/process/submitting-patches.html#sign-your-work-the-developer-s-certificate-of-origin
**DIFF_IN_COMMIT_MSG**
Avoid having diff content in commit message.
This causes problems when one tries to apply a file containing both
the changelog and the diff because patch(1) tries to apply the diff
which it found in the changelog.
See: https://lore.kernel.org/lkml/20150611134006.9df79a893e3636019ad2759e@linux-foundation.org/
**GERRIT_CHANGE_ID**
To be picked up by gerrit, the footer of the commit message might
have a Change-Id like::
Change-Id: Ic8aaa0728a43936cd4c6e1ed590e01ba8f0fbf5b
Signed-off-by: A. U. Thor <author@example.com>
The Change-Id line must be removed before submitting.
**GIT_COMMIT_ID**
The proper way to reference a commit id is:
commit <12+ chars of sha1> ("<title line>")
An example may be::
Commit e21d2170f36602ae2708 ("video: remove unnecessary
platform_set_drvdata()") removed the unnecessary
platform_set_drvdata(), but left the variable "dev" unused,
delete it.
See: https://www.kernel.org/doc/html/latest/process/submitting-patches.html#describe-your-changes
Comparison style
----------------
**ASSIGN_IN_IF**
Do not use assignments in if condition.
Example::
if ((foo = bar(...)) < BAZ) {
should be written as::
foo = bar(...);
if (foo < BAZ) {
**BOOL_COMPARISON**
Comparisons of A to true and false are better written
as A and !A.
See: https://lore.kernel.org/lkml/1365563834.27174.12.camel@joe-AO722/
**COMPARISON_TO_NULL**
Comparisons to NULL in the form (foo == NULL) or (foo != NULL)
are better written as (!foo) and (foo).
**CONSTANT_COMPARISON**
Comparisons with a constant or upper case identifier on the left
side of the test should be avoided.
Macros, Attributes and Symbols
------------------------------
**ARRAY_SIZE**
The ARRAY_SIZE(foo) macro should be preferred over
sizeof(foo)/sizeof(foo[0]) for finding number of elements in an
array.
The macro is defined in include/linux/kernel.h::
#define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0]))
**AVOID_EXTERNS**
Function prototypes don't need to be declared extern in .h
files. It's assumed by the compiler and is unnecessary.
**AVOID_L_PREFIX**
Local symbol names that are prefixed with `.L` should be avoided,
as this has special meaning for the assembler; a symbol entry will
not be emitted into the symbol table. This can prevent `objtool`
from generating correct unwind info.
Symbols with STB_LOCAL binding may still be used, and `.L` prefixed
local symbol names are still generally usable within a function,
but `.L` prefixed local symbol names should not be used to denote
the beginning or end of code regions via
`SYM_CODE_START_LOCAL`/`SYM_CODE_END`
**BIT_MACRO**
Defines like: 1 << <digit> could be BIT(digit).
The BIT() macro is defined in include/linux/bitops.h::
#define BIT(nr) (1UL << (nr))
**CONST_READ_MOSTLY**
When a variable is tagged with the __read_mostly annotation, it is a
signal to the compiler that accesses to the variable will be mostly
reads and rarely(but NOT never) a write.
const __read_mostly does not make any sense as const data is already
read-only. The __read_mostly annotation thus should be removed.
**DATE_TIME**
It is generally desirable that building the same source code with
the same set of tools is reproducible, i.e. the output is always
exactly the same.
The kernel does *not* use the ``__DATE__`` and ``__TIME__`` macros,
and enables warnings if they are used as they can lead to
non-deterministic builds.
See: https://www.kernel.org/doc/html/latest/kbuild/reproducible-builds.html#timestamps
**DEFINE_ARCH_HAS**
The ARCH_HAS_xyz and ARCH_HAVE_xyz patterns are wrong.
For big conceptual features use Kconfig symbols instead. And for
smaller things where we have compatibility fallback functions but
want architectures able to override them with optimized ones, we
should either use weak functions (appropriate for some cases), or
the symbol that protects them should be the same symbol we use.
See: https://lore.kernel.org/lkml/CA+55aFycQ9XJvEOsiM3txHL5bjUc8CeKWJNR_H+MiicaddB42Q@mail.gmail.com/
**INIT_ATTRIBUTE**
Const init definitions should use __initconst instead of
__initdata.
Similarly init definitions without const require a separate
use of const.
**INLINE_LOCATION**
The inline keyword should sit between storage class and type.
For example, the following segment::
inline static int example_function(void)
{
...
}
should be::
static inline int example_function(void)
{
...
}
**MULTISTATEMENT_MACRO_USE_DO_WHILE**
Macros with multiple statements should be enclosed in a
do - while block. Same should also be the case for macros
starting with `if` to avoid logic defects::
#define macrofun(a, b, c) \
do { \
if (a == 5) \
do_this(b, c); \
} while (0)
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#macros-enums-and-rtl
**WEAK_DECLARATION**
Using weak declarations like __attribute__((weak)) or __weak
can have unintended link defects. Avoid using them.
Functions and Variables
-----------------------
**CAMELCASE**
Avoid CamelCase Identifiers.
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#naming
**FUNCTION_WITHOUT_ARGS**
Function declarations without arguments like::
int foo()
should be::
int foo(void)
**GLOBAL_INITIALISERS**
Global variables should not be initialized explicitly to
0 (or NULL, false, etc.). Your compiler (or rather your
loader, which is responsible for zeroing out the relevant
sections) automatically does it for you.
**INITIALISED_STATIC**
Static variables should not be initialized explicitly to zero.
Your compiler (or rather your loader) automatically does
it for you.
**RETURN_PARENTHESES**
return is not a function and as such doesn't need parentheses::
return (bar);
can simply be::
return bar;
Spacing and Brackets
--------------------
**ASSIGNMENT_CONTINUATIONS**
Assignment operators should not be written at the start of a
line but should follow the operand at the previous line.
**BRACES**
The placement of braces is stylistically incorrect.
The preferred way is to put the opening brace last on the line,
and put the closing brace first::
if (x is true) {
we do y
}
This applies for all non-functional blocks.
However, there is one special case, namely functions: they have the
opening brace at the beginning of the next line, thus::
int function(int x)
{
body of function
}
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#placing-braces-and-spaces
**BRACKET_SPACE**
Whitespace before opening bracket '[' is prohibited.
There are some exceptions:
1. With a type on the left::
;int [] a;
2. At the beginning of a line for slice initialisers::
[0...10] = 5,
3. Inside a curly brace::
= { [0...10] = 5 }
**CODE_INDENT**
Code indent should use tabs instead of spaces.
Outside of comments, documentation and Kconfig,
spaces are never used for indentation.
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#indentation
**CONCATENATED_STRING**
Concatenated elements should have a space in between.
Example::
printk(KERN_INFO"bar");
should be::
printk(KERN_INFO "bar");
**ELSE_AFTER_BRACE**
`else {` should follow the closing block `}` on the same line.
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#placing-braces-and-spaces
**LINE_SPACING**
Vertical space is wasted given the limited number of lines an
editor window can display when multiple blank lines are used.
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#spaces
**OPEN_BRACE**
The opening brace should be following the function definitions on the
next line. For any non-functional block it should be on the same line
as the last construct.
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#placing-braces-and-spaces
**POINTER_LOCATION**
When using pointer data or a function that returns a pointer type,
the preferred use of * is adjacent to the data name or function name
and not adjacent to the type name.
Examples::
char *linux_banner;
unsigned long long memparse(char *ptr, char **retptr);
char *match_strdup(substring_t *s);
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#spaces
**SPACING**
Whitespace style used in the kernel sources is described in kernel docs.
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#spaces
**SWITCH_CASE_INDENT_LEVEL**
switch should be at the same indent as case.
Example::
switch (suffix) {
case 'G':
case 'g':
mem <<= 30;
break;
case 'M':
case 'm':
mem <<= 20;
break;
case 'K':
case 'k':
mem <<= 10;
/* fall through */
default:
break;
}
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#indentation
**TRAILING_WHITESPACE**
Trailing whitespace should always be removed.
Some editors highlight the trailing whitespace and cause visual
distractions when editing files.
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#spaces
**WHILE_AFTER_BRACE**
while should follow the closing bracket on the same line::
do {
...
} while(something);
See: https://www.kernel.org/doc/html/latest/process/coding-style.html#placing-braces-and-spaces
Others
------
**CONFIG_DESCRIPTION**
Kconfig symbols should have a help text which fully describes
it.
**CORRUPTED_PATCH**
The patch seems to be corrupted or lines are wrapped.
Please regenerate the patch file before sending it to the maintainer.
**DOS_LINE_ENDINGS**
For DOS-formatted patches, there are extra ^M symbols at the end of
the line. These should be removed.
**EXECUTE_PERMISSIONS**
There is no reason for source files to be executable. The executable
bit can be removed safely.
**NON_OCTAL_PERMISSIONS**
Permission bits should use 4 digit octal permissions (like 0700 or 0444).
Avoid using any other base like decimal.
**NOT_UNIFIED_DIFF**
The patch file does not appear to be in unified-diff format. Please
regenerate the patch file before sending it to the maintainer.
**PRINTF_0XDECIMAL**
Prefixing 0x with decimal output is defective and should be corrected.
**TRAILING_STATEMENTS**
Trailing statements (for example after any conditional) should be
on the next line.
Like::
if (x == y) break;
should be::
if (x == y)
break;

View file

@ -54,5 +54,6 @@ Refactoring
.. toctree::
:maxdepth: 1
checkpatch
coccinelle
moveconfig

View file

@ -36,10 +36,17 @@ menu "SATA/SCSI device support"
config AHCI_PCI
bool "Support for PCI-based AHCI controller"
depends on DM_PCI
depends on DM_SCSI
help
Enables support for the PCI-based AHCI controller.
config SPL_AHCI_PCI
bool "Support for PCI-based AHCI controller for SPL"
depends on SPL
depends on SPL_PCI
depends on SPL_SATA_SUPPORT && DM_SCSI
config SATA_CEVA
bool "Ceva Sata controller"
depends on AHCI

View file

@ -5,7 +5,7 @@
obj-$(CONFIG_DWC_AHCI) += dwc_ahci.o
obj-$(CONFIG_AHCI) += ahci-uclass.o
obj-$(CONFIG_AHCI_PCI) += ahci-pci.o
obj-$(CONFIG_$(SPL_)AHCI_PCI) += ahci-pci.o
obj-$(CONFIG_SCSI_AHCI) += ahci.o
obj-$(CONFIG_DWC_AHSATA) += dwc_ahsata.o
obj-$(CONFIG_FSL_SATA) += fsl_sata.o

View file

@ -1,5 +1,7 @@
menu "Hardware crypto devices"
source drivers/crypto/hash/Kconfig
source drivers/crypto/fsl/Kconfig
endmenu

View file

@ -6,3 +6,4 @@
obj-$(CONFIG_EXYNOS_ACE_SHA) += ace_sha.o
obj-y += rsa_mod_exp/
obj-y += fsl/
obj-y += hash/

View file

@ -0,0 +1,16 @@
config DM_HASH
bool "Enable Driver Model for Hash"
depends on DM
help
If you want to use driver model for Hash, say Y.
config HASH_SOFTWARE
bool "Enable driver for Hash in software"
depends on DM_HASH
depends on MD5
depends on SHA1
depends on SHA256
depends on SHA512_ALGO
help
Enable driver for hashing operations in software. Currently
it support multiple hash algorithm including CRC/MD5/SHA.

View file

@ -0,0 +1,6 @@
# SPDX-License-Identifier: GPL-2.0+
#
# Copyright (c) 2021 ASPEED Technology Inc.
obj-$(CONFIG_DM_HASH) += hash-uclass.o
obj-$(CONFIG_HASH_SOFTWARE) += hash_sw.o

View file

@ -0,0 +1,121 @@
// SPDX-License-Identifier: GPL-2.0+
/*
* Copyright (c) 2021 ASPEED Technology Inc.
* Author: ChiaWei Wang <chiawei_wang@aspeedtech.com>
*/
#define LOG_CATEGORY UCLASS_HASH
#include <common.h>
#include <dm.h>
#include <asm/global_data.h>
#include <u-boot/hash.h>
#include <errno.h>
#include <fdtdec.h>
#include <malloc.h>
#include <asm/io.h>
#include <linux/list.h>
struct hash_info {
char *name;
uint32_t digest_size;
};
static const struct hash_info hash_info[HASH_ALGO_NUM] = {
[HASH_ALGO_CRC16_CCITT] = { "crc16-ccitt", 2 },
[HASH_ALGO_CRC32] = { "crc32", 4 },
[HASH_ALGO_MD5] = { "md5", 16 },
[HASH_ALGO_SHA1] = { "sha1", 20 },
[HASH_ALGO_SHA256] = { "sha256", 32 },
[HASH_ALGO_SHA384] = { "sha384", 48 },
[HASH_ALGO_SHA512] = { "sha512", 64},
};
enum HASH_ALGO hash_algo_lookup_by_name(const char *name)
{
int i;
if (!name)
return HASH_ALGO_INVALID;
for (i = 0; i < HASH_ALGO_NUM; ++i)
if (!strcmp(name, hash_info[i].name))
return i;
return HASH_ALGO_INVALID;
}
ssize_t hash_algo_digest_size(enum HASH_ALGO algo)
{
if (algo >= HASH_ALGO_NUM)
return -EINVAL;
return hash_info[algo].digest_size;
}
const char *hash_algo_name(enum HASH_ALGO algo)
{
if (algo >= HASH_ALGO_NUM)
return NULL;
return hash_info[algo].name;
}
int hash_digest(struct udevice *dev, enum HASH_ALGO algo,
const void *ibuf, const uint32_t ilen,
void *obuf)
{
struct hash_ops *ops = (struct hash_ops *)device_get_ops(dev);
if (!ops->hash_digest)
return -ENOSYS;
return ops->hash_digest(dev, algo, ibuf, ilen, obuf);
}
int hash_digest_wd(struct udevice *dev, enum HASH_ALGO algo,
const void *ibuf, const uint32_t ilen,
void *obuf, uint32_t chunk_sz)
{
struct hash_ops *ops = (struct hash_ops *)device_get_ops(dev);
if (!ops->hash_digest_wd)
return -ENOSYS;
return ops->hash_digest_wd(dev, algo, ibuf, ilen, obuf, chunk_sz);
}
int hash_init(struct udevice *dev, enum HASH_ALGO algo, void **ctxp)
{
struct hash_ops *ops = (struct hash_ops *)device_get_ops(dev);
if (!ops->hash_init)
return -ENOSYS;
return ops->hash_init(dev, algo, ctxp);
}
int hash_update(struct udevice *dev, void *ctx, const void *ibuf, const uint32_t ilen)
{
struct hash_ops *ops = (struct hash_ops *)device_get_ops(dev);
if (!ops->hash_update)
return -ENOSYS;
return ops->hash_update(dev, ctx, ibuf, ilen);
}
int hash_finish(struct udevice *dev, void *ctx, void *obuf)
{
struct hash_ops *ops = (struct hash_ops *)device_get_ops(dev);
if (!ops->hash_finish)
return -ENOSYS;
return ops->hash_finish(dev, ctx, obuf);
}
UCLASS_DRIVER(hash) = {
.id = UCLASS_HASH,
.name = "hash",
};

View file

@ -0,0 +1,301 @@
// SPDX-License-Identifier: GPL-2.0+
/*
* Copyright (c) 2021 ASPEED Technology Inc.
* Author: ChiaWei Wang <chiawei_wang@aspeedtech.com>
*/
#include <config.h>
#include <common.h>
#include <dm.h>
#include <log.h>
#include <malloc.h>
#include <watchdog.h>
#include <u-boot/hash.h>
#include <u-boot/crc.h>
#include <u-boot/md5.h>
#include <u-boot/sha1.h>
#include <u-boot/sha256.h>
#include <u-boot/sha512.h>
/* CRC16-CCITT */
static void hash_init_crc16_ccitt(void *ctx)
{
*((uint16_t *)ctx) = 0;
}
static void hash_update_crc16_ccitt(void *ctx, const void *ibuf, uint32_t ilen)
{
*((uint16_t *)ctx) = crc16_ccitt(*((uint16_t *)ctx), ibuf, ilen);
}
static void hash_finish_crc16_ccitt(void *ctx, void *obuf)
{
*((uint16_t *)obuf) = *((uint16_t *)ctx);
}
/* CRC32 */
static void hash_init_crc32(void *ctx)
{
*((uint32_t *)ctx) = 0;
}
static void hash_update_crc32(void *ctx, const void *ibuf, uint32_t ilen)
{
*((uint32_t *)ctx) = crc32(*((uint32_t *)ctx), ibuf, ilen);
}
static void hash_finish_crc32(void *ctx, void *obuf)
{
*((uint32_t *)obuf) = *((uint32_t *)ctx);
}
/* MD5 */
static void hash_init_md5(void *ctx)
{
MD5Init((struct MD5Context *)ctx);
}
static void hash_update_md5(void *ctx, const void *ibuf, uint32_t ilen)
{
MD5Update((struct MD5Context *)ctx, ibuf, ilen);
}
static void hash_finish_md5(void *ctx, void *obuf)
{
MD5Final(obuf, (struct MD5Context *)ctx);
}
/* SHA1 */
static void hash_init_sha1(void *ctx)
{
sha1_starts((sha1_context *)ctx);
}
static void hash_update_sha1(void *ctx, const void *ibuf, uint32_t ilen)
{
sha1_update((sha1_context *)ctx, ibuf, ilen);
}
static void hash_finish_sha1(void *ctx, void *obuf)
{
sha1_finish((sha1_context *)ctx, obuf);
}
/* SHA256 */
static void hash_init_sha256(void *ctx)
{
sha256_starts((sha256_context *)ctx);
}
static void hash_update_sha256(void *ctx, const void *ibuf, uint32_t ilen)
{
sha256_update((sha256_context *)ctx, ibuf, ilen);
}
static void hash_finish_sha256(void *ctx, void *obuf)
{
sha256_finish((sha256_context *)ctx, obuf);
}
/* SHA384 */
static void hash_init_sha384(void *ctx)
{
sha384_starts((sha512_context *)ctx);
}
static void hash_update_sha384(void *ctx, const void *ibuf, uint32_t ilen)
{
sha384_update((sha512_context *)ctx, ibuf, ilen);
}
static void hash_finish_sha384(void *ctx, void *obuf)
{
sha384_finish((sha512_context *)ctx, obuf);
}
/* SHA512 */
static void hash_init_sha512(void *ctx)
{
sha512_starts((sha512_context *)ctx);
}
static void hash_update_sha512(void *ctx, const void *ibuf, uint32_t ilen)
{
sha512_update((sha512_context *)ctx, ibuf, ilen);
}
static void hash_finish_sha512(void *ctx, void *obuf)
{
sha512_finish((sha512_context *)ctx, obuf);
}
struct sw_hash_ctx {
enum HASH_ALGO algo;
uint8_t algo_ctx[];
};
struct sw_hash_impl {
void (*init)(void *ctx);
void (*update)(void *ctx, const void *ibuf, uint32_t ilen);
void (*finish)(void *ctx, void *obuf);
uint32_t ctx_alloc_sz;
};
static struct sw_hash_impl sw_hash_impl[HASH_ALGO_NUM] = {
[HASH_ALGO_CRC16_CCITT] = {
.init = hash_init_crc16_ccitt,
.update = hash_update_crc16_ccitt,
.finish = hash_finish_crc16_ccitt,
.ctx_alloc_sz = sizeof(uint16_t),
},
[HASH_ALGO_CRC32] = {
.init = hash_init_crc32,
.update = hash_update_crc32,
.finish = hash_finish_crc32,
.ctx_alloc_sz = sizeof(uint32_t),
},
[HASH_ALGO_MD5] = {
.init = hash_init_md5,
.update = hash_update_md5,
.finish = hash_finish_md5,
.ctx_alloc_sz = sizeof(struct MD5Context),
},
[HASH_ALGO_SHA1] = {
.init = hash_init_sha1,
.update = hash_update_sha1,
.finish = hash_finish_sha1,
.ctx_alloc_sz = sizeof(sha1_context),
},
[HASH_ALGO_SHA256] = {
.init = hash_init_sha256,
.update = hash_update_sha256,
.finish = hash_finish_sha256,
.ctx_alloc_sz = sizeof(sha256_context),
},
[HASH_ALGO_SHA384] = {
.init = hash_init_sha384,
.update = hash_update_sha384,
.finish = hash_finish_sha384,
.ctx_alloc_sz = sizeof(sha512_context),
},
[HASH_ALGO_SHA512] = {
.init = hash_init_sha512,
.update = hash_update_sha512,
.finish = hash_finish_sha512,
.ctx_alloc_sz = sizeof(sha512_context),
},
};
static int sw_hash_init(struct udevice *dev, enum HASH_ALGO algo, void **ctxp)
{
struct sw_hash_ctx *hash_ctx;
struct sw_hash_impl *hash_impl = &sw_hash_impl[algo];
hash_ctx = malloc(sizeof(hash_ctx->algo) + hash_impl->ctx_alloc_sz);
if (!hash_ctx)
return -ENOMEM;
hash_ctx->algo = algo;
hash_impl->init(hash_ctx->algo_ctx);
*ctxp = hash_ctx;
return 0;
}
static int sw_hash_update(struct udevice *dev, void *ctx, const void *ibuf, uint32_t ilen)
{
struct sw_hash_ctx *hash_ctx = ctx;
struct sw_hash_impl *hash_impl = &sw_hash_impl[hash_ctx->algo];
hash_impl->update(hash_ctx->algo_ctx, ibuf, ilen);
return 0;
}
static int sw_hash_finish(struct udevice *dev, void *ctx, void *obuf)
{
struct sw_hash_ctx *hash_ctx = ctx;
struct sw_hash_impl *hash_impl = &sw_hash_impl[hash_ctx->algo];
hash_impl->finish(hash_ctx->algo_ctx, obuf);
free(ctx);
return 0;
}
static int sw_hash_digest_wd(struct udevice *dev, enum HASH_ALGO algo,
const void *ibuf, const uint32_t ilen,
void *obuf, uint32_t chunk_sz)
{
int rc;
void *ctx;
const void *cur, *end;
uint32_t chunk;
rc = sw_hash_init(dev, algo, &ctx);
if (rc)
return rc;
if (CONFIG_IS_ENABLED(HW_WATCHDOG) || CONFIG_IS_ENABLED(WATCHDOG)) {
cur = ibuf;
end = ibuf + ilen;
while (cur < end) {
chunk = end - cur;
if (chunk > chunk_sz)
chunk = chunk_sz;
rc = sw_hash_update(dev, ctx, cur, chunk);
if (rc)
return rc;
cur += chunk;
WATCHDOG_RESET();
}
} else {
rc = sw_hash_update(dev, ctx, ibuf, ilen);
if (rc)
return rc;
}
rc = sw_hash_finish(dev, ctx, obuf);
if (rc)
return rc;
return 0;
}
static int sw_hash_digest(struct udevice *dev, enum HASH_ALGO algo,
const void *ibuf, const uint32_t ilen,
void *obuf)
{
/* re-use the watchdog version with input length as the chunk_sz */
return sw_hash_digest_wd(dev, algo, ibuf, ilen, obuf, ilen);
}
static const struct hash_ops hash_ops_sw = {
.hash_init = sw_hash_init,
.hash_update = sw_hash_update,
.hash_finish = sw_hash_finish,
.hash_digest_wd = sw_hash_digest_wd,
.hash_digest = sw_hash_digest,
};
U_BOOT_DRIVER(hash_sw) = {
.name = "hash_sw",
.id = UCLASS_HASH,
.ops = &hash_ops_sw,
.flags = DM_FLAG_PRE_RELOC,
};
U_BOOT_DRVINFO(hash_sw) = {
.name = "hash_sw",
};

View file

@ -43,11 +43,21 @@ enum ds_type {
#define RTC_SEC_BIT_CH 0x80 /* Clock Halt (in Register 0) */
/* DS1307-specific bits */
#define RTC_CTL_BIT_RS0 0x01 /* Rate select 0 */
#define RTC_CTL_BIT_RS1 0x02 /* Rate select 1 */
#define RTC_CTL_BIT_SQWE 0x10 /* Square Wave Enable */
#define RTC_CTL_BIT_OUT 0x80 /* Output Control */
/* DS1337-specific bits */
#define DS1337_CTL_BIT_RS1 0x08 /* Rate select 1 */
#define DS1337_CTL_BIT_RS2 0x10 /* Rate select 2 */
#define DS1337_CTL_BIT_EOSC 0x80 /* Enable Oscillator */
/* DS1340-specific bits */
#define DS1340_SEC_BIT_EOSC 0x80 /* Enable Oscillator */
#define DS1340_CTL_BIT_OUT 0x80 /* Output Control */
/* MCP7941X-specific bits */
#define MCP7941X_BIT_ST 0x80
#define MCP7941X_BIT_VBATEN 0x08
@ -261,9 +271,25 @@ read_rtc:
buf[RTC_SEC_REG_ADDR]);
return -1;
}
}
if (type == m41t11) {
} else if (type == ds_1337) {
if (buf[RTC_CTL_REG_ADDR] & DS1337_CTL_BIT_EOSC) {
printf("### Warning: RTC oscillator has stopped\n");
/* clear the not oscillator enable (~EOSC) flag */
buf[RTC_CTL_REG_ADDR] &= ~DS1337_CTL_BIT_EOSC;
dm_i2c_reg_write(dev, RTC_CTL_REG_ADDR,
buf[RTC_CTL_REG_ADDR]);
return -1;
}
} else if (type == ds_1340) {
if (buf[RTC_SEC_REG_ADDR] & DS1340_SEC_BIT_EOSC) {
printf("### Warning: RTC oscillator has stopped\n");
/* clear the not oscillator enable (~EOSC) flag */
buf[RTC_SEC_REG_ADDR] &= ~DS1340_SEC_BIT_EOSC;
dm_i2c_reg_write(dev, RTC_SEC_REG_ADDR,
buf[RTC_SEC_REG_ADDR]);
return -1;
}
} else if (type == m41t11) {
/* clock halted? turn it on, so clock can tick. */
if (buf[RTC_SEC_REG_ADDR] & RTC_SEC_BIT_CH) {
buf[RTC_SEC_REG_ADDR] &= ~RTC_SEC_BIT_CH;
@ -273,9 +299,7 @@ read_rtc:
buf[RTC_SEC_REG_ADDR]);
goto read_rtc;
}
}
if (type == mcp794xx) {
} else if (type == mcp794xx) {
/* make sure that the backup battery is enabled */
if (!(buf[RTC_DAY_REG_ADDR] & MCP7941X_BIT_VBATEN)) {
dm_i2c_reg_write(dev, RTC_DAY_REG_ADDR,
@ -314,18 +338,37 @@ read_rtc:
static int ds1307_rtc_reset(struct udevice *dev)
{
int ret;
enum ds_type type = dev_get_driver_data(dev);
/* clear Clock Halt */
/*
* reset clock/oscillator in the seconds register:
* on DS1307 bit 7 enables Clock Halt (CH),
* on DS1340 bit 7 disables the oscillator (not EOSC)
* on MCP794xx bit 7 enables Start Oscillator (ST)
*/
ret = dm_i2c_reg_write(dev, RTC_SEC_REG_ADDR, 0x00);
if (ret < 0)
return ret;
ret = dm_i2c_reg_write(dev, RTC_CTL_REG_ADDR,
RTC_CTL_BIT_SQWE | RTC_CTL_BIT_RS1 |
RTC_CTL_BIT_RS0);
if (ret < 0)
return ret;
return 0;
if (type == ds_1307) {
/* Write control register in order to enable square-wave
* output (SQWE) and set a default rate of 32.768kHz (RS1|RS0).
*/
ret = dm_i2c_reg_write(dev, RTC_CTL_REG_ADDR,
RTC_CTL_BIT_SQWE | RTC_CTL_BIT_RS1 |
RTC_CTL_BIT_RS0);
} else if (type == ds_1337) {
/* Write control register in order to enable oscillator output
* (not EOSC) and set a default rate of 32.768kHz (RS2|RS1).
*/
ret = dm_i2c_reg_write(dev, RTC_CTL_REG_ADDR,
DS1337_CTL_BIT_RS2 | DS1337_CTL_BIT_RS1);
} else if (type == ds_1340 || type == mcp794xx || type == m41t11) {
/* Reset clock calibration, frequency test and output level. */
ret = dm_i2c_reg_write(dev, RTC_CTL_REG_ADDR, 0x00);
}
return ret;
}
static int ds1307_probe(struct udevice *dev)

View file

@ -22,4 +22,31 @@
/* Generate initrd atag for downstream kernel (others are copied in stemmy.c) */
#define CONFIG_INITRD_TAG
/* Linux does not boot if FDT / initrd is loaded to end of RAM */
#define BOOT_ENV \
"fdt_high=0x6000000\0" \
"initrd_high=0x6000000\0"
#define CONSOLE_ENV \
"stdin=serial\0" \
"stdout=serial,vidconsole\0" \
"stderr=serial,vidconsole\0"
#define FASTBOOT_ENV \
"fastboot_partition_alias_boot=Kernel\0" \
"fastboot_partition_alias_recovery=Kernel2\0" \
"fastboot_partition_alias_system=SYSTEM\0" \
"fastboot_partition_alias_cache=CACHEFS\0" \
"fastboot_partition_alias_hidden=HIDDEN\0" \
"fastboot_partition_alias_userdata=DATAFS\0"
#define BOOTCMD_ENV \
"fastbootcmd=echo '*** FASTBOOT MODE ***'; fastboot usb 0\0"
#define CONFIG_EXTRA_ENV_SETTINGS \
BOOT_ENV \
CONSOLE_ENV \
FASTBOOT_ENV \
BOOTCMD_ENV
#endif

View file

@ -54,6 +54,7 @@ enum uclass_id {
UCLASS_FIRMWARE, /* Firmware */
UCLASS_FS_FIRMWARE_LOADER, /* Generic loader */
UCLASS_GPIO, /* Bank of general-purpose I/O pins */
UCLASS_HASH, /* Hash device */
UCLASS_HWSPINLOCK, /* Hardware semaphores */
UCLASS_I2C, /* I2C bus */
UCLASS_I2C_EEPROM, /* I2C EEPROM device */

61
include/u-boot/hash.h Normal file
View file

@ -0,0 +1,61 @@
/* SPDX-License-Identifier: GPL-2.0+ */
/*
* Copyright (c) 2021 ASPEED Technology Inc.
*/
#ifndef _UBOOT_HASH_H
#define _UBOOT_HASH_H
enum HASH_ALGO {
HASH_ALGO_CRC16_CCITT,
HASH_ALGO_CRC32,
HASH_ALGO_MD5,
HASH_ALGO_SHA1,
HASH_ALGO_SHA256,
HASH_ALGO_SHA384,
HASH_ALGO_SHA512,
HASH_ALGO_NUM,
HASH_ALGO_INVALID = 0xffffffff,
};
/* general APIs for hash algo information */
enum HASH_ALGO hash_algo_lookup_by_name(const char *name);
ssize_t hash_algo_digest_size(enum HASH_ALGO algo);
const char *hash_algo_name(enum HASH_ALGO algo);
/* device-dependent APIs */
int hash_digest(struct udevice *dev, enum HASH_ALGO algo,
const void *ibuf, const uint32_t ilen,
void *obuf);
int hash_digest_wd(struct udevice *dev, enum HASH_ALGO algo,
const void *ibuf, const uint32_t ilen,
void *obuf, uint32_t chunk_sz);
int hash_init(struct udevice *dev, enum HASH_ALGO algo, void **ctxp);
int hash_update(struct udevice *dev, void *ctx, const void *ibuf, const uint32_t ilen);
int hash_finish(struct udevice *dev, void *ctx, void *obuf);
/*
* struct hash_ops - Driver model for Hash operations
*
* The uclass interface is implemented by all hash devices
* which use driver model.
*/
struct hash_ops {
/* progressive operations */
int (*hash_init)(struct udevice *dev, enum HASH_ALGO algo, void **ctxp);
int (*hash_update)(struct udevice *dev, void *ctx, const void *ibuf, const uint32_t ilen);
int (*hash_finish)(struct udevice *dev, void *ctx, void *obuf);
/* all-in-one operation */
int (*hash_digest)(struct udevice *dev, enum HASH_ALGO algo,
const void *ibuf, const uint32_t ilen,
void *obuf);
/* all-in-one operation with watchdog triggering every chunk_sz */
int (*hash_digest_wd)(struct udevice *dev, enum HASH_ALGO algo,
const void *ibuf, const uint32_t ilen,
void *obuf, uint32_t chunk_sz);
};
#endif

View file

@ -17,6 +17,10 @@ struct MD5Context {
};
};
void MD5Init(struct MD5Context *ctx);
void MD5Update(struct MD5Context *ctx, unsigned char const *buf, unsigned len);
void MD5Final(unsigned char digest[16], struct MD5Context *ctx);
/*
* Calculate and store in 'output' the MD5 digest of 'len' bytes at
* 'input'. 'output' must have enough space to hold 16 bytes.

View file

@ -55,7 +55,7 @@ byteReverse(unsigned char *buf, unsigned longs)
* Start MD5 accumulation. Set bit count to 0 and buffer to mysterious
* initialization constants.
*/
static void
void
MD5Init(struct MD5Context *ctx)
{
ctx->buf[0] = 0x67452301;
@ -71,7 +71,7 @@ MD5Init(struct MD5Context *ctx)
* Update context to reflect the concatenation of another buffer full
* of bytes.
*/
static void
void
MD5Update(struct MD5Context *ctx, unsigned char const *buf, unsigned len)
{
register __u32 t;
@ -120,7 +120,7 @@ MD5Update(struct MD5Context *ctx, unsigned char const *buf, unsigned len)
* Final wrapup - pad to 64-byte boundary with the bit pattern
* 1 0* (64-bit count of bits processed, MSB-first)
*/
static void
void
MD5Final(unsigned char digest[16], struct MD5Context *ctx)
{
unsigned int count;

View file

@ -19,24 +19,6 @@
#include <openssl/evp.h>
#include <openssl/engine.h>
#if OPENSSL_VERSION_NUMBER >= 0x10000000L
#define HAVE_ERR_REMOVE_THREAD_STATE
#endif
#if OPENSSL_VERSION_NUMBER < 0x10100000L || \
(defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER < 0x02070000fL)
static void RSA_get0_key(const RSA *r,
const BIGNUM **n, const BIGNUM **e, const BIGNUM **d)
{
if (n != NULL)
*n = r->n;
if (e != NULL)
*e = r->e;
if (d != NULL)
*d = r->d;
}
#endif
static int rsa_err(const char *msg)
{
unsigned long sslErr = ERR_get_error();
@ -272,7 +254,7 @@ static int rsa_engine_get_priv_key(const char *keydir, const char *name,
else if (keydir)
snprintf(key_id, sizeof(key_id),
"%s",
name);
name ? name : "");
else if (keyfile)
snprintf(key_id, sizeof(key_id), "%s", keyfile);
else
@ -314,24 +296,11 @@ static int rsa_init(void)
{
int ret;
#if OPENSSL_VERSION_NUMBER < 0x10100000L || \
(defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER < 0x02070000fL)
ret = SSL_library_init();
#else
ret = OPENSSL_init_ssl(0, NULL);
#endif
if (!ret) {
fprintf(stderr, "Failure to init SSL library\n");
return -1;
}
#if OPENSSL_VERSION_NUMBER < 0x10100000L || \
(defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER < 0x02070000fL)
SSL_load_error_strings();
OpenSSL_add_all_algorithms();
OpenSSL_add_all_digests();
OpenSSL_add_all_ciphers();
#endif
return 0;
}
@ -347,8 +316,7 @@ static int rsa_engine_init(const char *engine_id, ENGINE **pe)
e = ENGINE_by_id(engine_id);
if (!e) {
fprintf(stderr, "Engine isn't available\n");
ret = -1;
goto err_engine_by_id;
return -1;
}
if (!ENGINE_init(e)) {
@ -381,29 +349,9 @@ err_set_rsa:
ENGINE_finish(e);
err_engine_init:
ENGINE_free(e);
err_engine_by_id:
#if OPENSSL_VERSION_NUMBER < 0x10100000L || \
(defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER < 0x02070000fL)
ENGINE_cleanup();
#endif
return ret;
}
static void rsa_remove(void)
{
#if OPENSSL_VERSION_NUMBER < 0x10100000L || \
(defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER < 0x02070000fL)
CRYPTO_cleanup_all_ex_data();
ERR_free_strings();
#ifdef HAVE_ERR_REMOVE_THREAD_STATE
ERR_remove_thread_state(NULL);
#else
ERR_remove_state(0);
#endif
EVP_cleanup();
#endif
}
static void rsa_engine_remove(ENGINE *e)
{
if (e) {
@ -476,12 +424,7 @@ static int rsa_sign_with_key(EVP_PKEY *pkey, struct padding_algo *padding_algo,
goto err_sign;
}
#if OPENSSL_VERSION_NUMBER < 0x10100000L || \
(defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER < 0x02070000fL)
EVP_MD_CTX_cleanup(context);
#else
EVP_MD_CTX_reset(context);
#endif
EVP_MD_CTX_reset(context);
EVP_MD_CTX_destroy(context);
debug("Got signature: %zu bytes, expected %d\n", size, EVP_PKEY_size(pkey));
@ -513,7 +456,7 @@ int rsa_sign(struct image_sign_info *info,
if (info->engine_id) {
ret = rsa_engine_init(info->engine_id, &e);
if (ret)
goto err_engine;
return ret;
}
ret = rsa_get_priv_key(info->keydir, info->keyname, info->keyfile,
@ -528,7 +471,6 @@ int rsa_sign(struct image_sign_info *info,
EVP_PKEY_free(pkey);
if (info->engine_id)
rsa_engine_remove(e);
rsa_remove();
return ret;
@ -537,8 +479,6 @@ err_sign:
err_priv:
if (info->engine_id)
rsa_engine_remove(e);
err_engine:
rsa_remove();
return ret;
}
@ -686,12 +626,8 @@ int rsa_add_verify_data(struct image_sign_info *info, void *keydest)
ret = rsa_get_pub_key(info->keydir, info->keyname, e, &pkey);
if (ret)
goto err_get_pub_key;
#if OPENSSL_VERSION_NUMBER < 0x10100000L || \
(defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER < 0x02070000fL)
rsa = EVP_PKEY_get1_RSA(pkey);
#else
rsa = EVP_PKEY_get0_RSA(pkey);
#endif
ret = rsa_get_params(rsa, &exponent, &n0_inv, &modulus, &r_squared);
if (ret)
goto err_get_params;
@ -761,10 +697,6 @@ done:
if (ret)
ret = ret == -FDT_ERR_NOSPACE ? -ENOSPC : -EIO;
err_get_params:
#if OPENSSL_VERSION_NUMBER < 0x10100000L || \
(defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER < 0x02070000fL)
RSA_free(rsa);
#endif
EVP_PKEY_free(pkey);
err_get_pub_key:
if (info->engine_id)

File diff suppressed because it is too large Load diff

296
scripts/spdxcheck.py Executable file
View file

@ -0,0 +1,296 @@
#!/usr/bin/env python3
# SPDX-License-Identifier: GPL-2.0
# Copyright Thomas Gleixner <tglx@linutronix.de>
from argparse import ArgumentParser
from ply import lex, yacc
import locale
import traceback
import sys
import git
import re
import os
class ParserException(Exception):
def __init__(self, tok, txt):
self.tok = tok
self.txt = txt
class SPDXException(Exception):
def __init__(self, el, txt):
self.el = el
self.txt = txt
class SPDXdata(object):
def __init__(self):
self.license_files = 0
self.exception_files = 0
self.licenses = [ ]
self.exceptions = { }
# Read the spdx data from the LICENSES directory
def read_spdxdata(repo):
# The subdirectories of LICENSES in the kernel source
# Note: exceptions needs to be parsed as last directory.
license_dirs = [ "preferred", "dual", "deprecated", "exceptions" ]
lictree = repo.head.commit.tree['LICENSES']
spdx = SPDXdata()
for d in license_dirs:
for el in lictree[d].traverse():
if not os.path.isfile(el.path):
continue
exception = None
for l in open(el.path).readlines():
if l.startswith('Valid-License-Identifier:'):
lid = l.split(':')[1].strip().upper()
if lid in spdx.licenses:
raise SPDXException(el, 'Duplicate License Identifier: %s' %lid)
else:
spdx.licenses.append(lid)
elif l.startswith('SPDX-Exception-Identifier:'):
exception = l.split(':')[1].strip().upper()
spdx.exceptions[exception] = []
elif l.startswith('SPDX-Licenses:'):
for lic in l.split(':')[1].upper().strip().replace(' ', '').replace('\t', '').split(','):
if not lic in spdx.licenses:
raise SPDXException(None, 'Exception %s missing license %s' %(exception, lic))
spdx.exceptions[exception].append(lic)
elif l.startswith("License-Text:"):
if exception:
if not len(spdx.exceptions[exception]):
raise SPDXException(el, 'Exception %s is missing SPDX-Licenses' %exception)
spdx.exception_files += 1
else:
spdx.license_files += 1
break
return spdx
class id_parser(object):
reserved = [ 'AND', 'OR', 'WITH' ]
tokens = [ 'LPAR', 'RPAR', 'ID', 'EXC' ] + reserved
precedence = ( ('nonassoc', 'AND', 'OR'), )
t_ignore = ' \t'
def __init__(self, spdx):
self.spdx = spdx
self.lasttok = None
self.lastid = None
self.lexer = lex.lex(module = self, reflags = re.UNICODE)
# Initialize the parser. No debug file and no parser rules stored on disk
# The rules are small enough to be generated on the fly
self.parser = yacc.yacc(module = self, write_tables = False, debug = False)
self.lines_checked = 0
self.checked = 0
self.spdx_valid = 0
self.spdx_errors = 0
self.curline = 0
self.deepest = 0
# Validate License and Exception IDs
def validate(self, tok):
id = tok.value.upper()
if tok.type == 'ID':
if not id in self.spdx.licenses:
raise ParserException(tok, 'Invalid License ID')
self.lastid = id
elif tok.type == 'EXC':
if id not in self.spdx.exceptions:
raise ParserException(tok, 'Invalid Exception ID')
if self.lastid not in self.spdx.exceptions[id]:
raise ParserException(tok, 'Exception not valid for license %s' %self.lastid)
self.lastid = None
elif tok.type != 'WITH':
self.lastid = None
# Lexer functions
def t_RPAR(self, tok):
r'\)'
self.lasttok = tok.type
return tok
def t_LPAR(self, tok):
r'\('
self.lasttok = tok.type
return tok
def t_ID(self, tok):
r'[A-Za-z.0-9\-+]+'
if self.lasttok == 'EXC':
print(tok)
raise ParserException(tok, 'Missing parentheses')
tok.value = tok.value.strip()
val = tok.value.upper()
if val in self.reserved:
tok.type = val
elif self.lasttok == 'WITH':
tok.type = 'EXC'
self.lasttok = tok.type
self.validate(tok)
return tok
def t_error(self, tok):
raise ParserException(tok, 'Invalid token')
def p_expr(self, p):
'''expr : ID
| ID WITH EXC
| expr AND expr
| expr OR expr
| LPAR expr RPAR'''
pass
def p_error(self, p):
if not p:
raise ParserException(None, 'Unfinished license expression')
else:
raise ParserException(p, 'Syntax error')
def parse(self, expr):
self.lasttok = None
self.lastid = None
self.parser.parse(expr, lexer = self.lexer)
def parse_lines(self, fd, maxlines, fname):
self.checked += 1
self.curline = 0
try:
for line in fd:
line = line.decode(locale.getpreferredencoding(False), errors='ignore')
self.curline += 1
if self.curline > maxlines:
break
self.lines_checked += 1
if line.find("SPDX-License-Identifier:") < 0:
continue
expr = line.split(':')[1].strip()
# Remove trailing comment closure
if line.strip().endswith('*/'):
expr = expr.rstrip('*/').strip()
# Remove trailing xml comment closure
if line.strip().endswith('-->'):
expr = expr.rstrip('-->').strip()
# Special case for SH magic boot code files
if line.startswith('LIST \"'):
expr = expr.rstrip('\"').strip()
self.parse(expr)
self.spdx_valid += 1
#
# Should we check for more SPDX ids in the same file and
# complain if there are any?
#
break
except ParserException as pe:
if pe.tok:
col = line.find(expr) + pe.tok.lexpos
tok = pe.tok.value
sys.stdout.write('%s: %d:%d %s: %s\n' %(fname, self.curline, col, pe.txt, tok))
else:
sys.stdout.write('%s: %d:0 %s\n' %(fname, self.curline, col, pe.txt))
self.spdx_errors += 1
def scan_git_tree(tree):
for el in tree.traverse():
# Exclude stuff which would make pointless noise
# FIXME: Put this somewhere more sensible
if el.path.startswith("LICENSES"):
continue
if el.path.find("license-rules.rst") >= 0:
continue
if not os.path.isfile(el.path):
continue
with open(el.path, 'rb') as fd:
parser.parse_lines(fd, args.maxlines, el.path)
def scan_git_subtree(tree, path):
for p in path.strip('/').split('/'):
tree = tree[p]
scan_git_tree(tree)
if __name__ == '__main__':
ap = ArgumentParser(description='SPDX expression checker')
ap.add_argument('path', nargs='*', help='Check path or file. If not given full git tree scan. For stdin use "-"')
ap.add_argument('-m', '--maxlines', type=int, default=15,
help='Maximum number of lines to scan in a file. Default 15')
ap.add_argument('-v', '--verbose', action='store_true', help='Verbose statistics output')
args = ap.parse_args()
# Sanity check path arguments
if '-' in args.path and len(args.path) > 1:
sys.stderr.write('stdin input "-" must be the only path argument\n')
sys.exit(1)
try:
# Use git to get the valid license expressions
repo = git.Repo(os.getcwd())
assert not repo.bare
# Initialize SPDX data
spdx = read_spdxdata(repo)
# Initialize the parser
parser = id_parser(spdx)
except SPDXException as se:
if se.el:
sys.stderr.write('%s: %s\n' %(se.el.path, se.txt))
else:
sys.stderr.write('%s\n' %se.txt)
sys.exit(1)
except Exception as ex:
sys.stderr.write('FAIL: %s\n' %ex)
sys.stderr.write('%s\n' %traceback.format_exc())
sys.exit(1)
try:
if len(args.path) and args.path[0] == '-':
stdin = os.fdopen(sys.stdin.fileno(), 'rb')
parser.parse_lines(stdin, args.maxlines, '-')
else:
if args.path:
for p in args.path:
if os.path.isfile(p):
parser.parse_lines(open(p, 'rb'), args.maxlines, p)
elif os.path.isdir(p):
scan_git_subtree(repo.head.reference.commit.tree, p)
else:
sys.stderr.write('path %s does not exist\n' %p)
sys.exit(1)
else:
# Full git tree scan
scan_git_tree(repo.head.commit.tree)
if args.verbose:
sys.stderr.write('\n')
sys.stderr.write('License files: %12d\n' %spdx.license_files)
sys.stderr.write('Exception files: %12d\n' %spdx.exception_files)
sys.stderr.write('License IDs %12d\n' %len(spdx.licenses))
sys.stderr.write('Exception IDs %12d\n' %len(spdx.exceptions))
sys.stderr.write('\n')
sys.stderr.write('Files checked: %12d\n' %parser.checked)
sys.stderr.write('Lines checked: %12d\n' %parser.lines_checked)
sys.stderr.write('Files with SPDX: %12d\n' %parser.spdx_valid)
sys.stderr.write('Files with errors: %12d\n' %parser.spdx_errors)
sys.exit(0)
except Exception as ex:
sys.stderr.write('FAIL: %s\n' %ex)
sys.stderr.write('%s\n' %traceback.format_exc())
sys.exit(1)

View file

@ -732,6 +732,12 @@ copy_file (int ifd, const char *datafile, int pad)
exit (EXIT_FAILURE);
}
if (sbuf.st_size == 0) {
fprintf (stderr, "%s: Input file %s is empty, bailing out\n",
params.cmdname, datafile);
exit (EXIT_FAILURE);
}
ptr = mmap(0, sbuf.st_size, PROT_READ, MAP_SHARED, dfd, 0);
if (ptr == MAP_FAILED) {
fprintf (stderr, "%s: Can't read %s: %s\n",