// SPDX-License-Identifier: (GPL-2.0+ OR MIT)
// Copyright (C) 2019 Icenowy Zheng <icenowy@aosc.xyz>
// Copyright (C) 2020 Martijn Braam <martijn@brixit.nl>
// Copyright (C) 2020 Ondrej Jirman <megous@megous.com>

#include "sun50i-a64.dtsi"
#include "sun50i-a64-cpu-opp.dtsi"

#include <dt-bindings/gpio/gpio.h>
#include <dt-bindings/input/input.h>
#include <dt-bindings/leds/common.h>
#include <dt-bindings/pwm/pwm.h>

/ {
	chassis-type = "handset";

	aliases {
		ethernet0 = &rtl8723cs;
		serial0 = &uart0;
	};

	backlight: backlight {
		compatible = "pwm-backlight";
		pwms = <&r_pwm 0 50000 PWM_POLARITY_INVERTED>;
		enable-gpios = <&pio 7 10 GPIO_ACTIVE_HIGH>; /* PH10 */
		power-supply = <&reg_ps>;
		/* Backlight configuration differs per PinePhone revision. */
	};

	bt_sco_codec: bt-sco-codec {
		#sound-dai-cells = <1>;
		compatible = "linux,bt-sco";
	};

	chosen {
		stdout-path = "serial0:115200n8";
	};

	leds {
		compatible = "gpio-leds";

		led-0 {
			function = LED_FUNCTION_INDICATOR;
			color = <LED_COLOR_ID_BLUE>;
			gpios = <&pio 3 20 GPIO_ACTIVE_HIGH>; /* PD20 */
		};

		led-1 {
			function = LED_FUNCTION_INDICATOR;
			color = <LED_COLOR_ID_GREEN>;
			gpios = <&pio 3 18 GPIO_ACTIVE_HIGH>; /* PD18 */
		};

		led-2 {
			function = LED_FUNCTION_INDICATOR;
			color = <LED_COLOR_ID_RED>;
			gpios = <&pio 3 19 GPIO_ACTIVE_HIGH>; /* PD19 */
		};
	};

	reg_ps: ps-regulator {
		compatible = "regulator-fixed";
		regulator-name = "ps";
		regulator-min-microvolt = <5000000>;
		regulator-max-microvolt = <5000000>;
		regulator-boot-on;
	};

	reg_vbat_wifi: vbat-wifi {
		compatible = "regulator-fixed";
		regulator-min-microvolt = <3300000>;
		regulator-max-microvolt = <3300000>;
		regulator-name = "vbat-wifi";
	};

	sgm3140: led-controller {
		compatible = "sgmicro,sgm3140";
		vin-supply = <&reg_dcdc1>;

		sgm3140_flash: led {
			function = LED_FUNCTION_FLASH;
			color = <LED_COLOR_ID_WHITE>;
			flash-max-timeout-us = <250000>;
		};
	};

	speaker_amp: audio-amplifier {
		compatible = "simple-audio-amplifier";
		enable-gpios = <&pio 2 7 GPIO_ACTIVE_HIGH>; /* PC7 */
		sound-name-prefix = "Speaker Amp";
	};

	vibrator {
		compatible = "gpio-vibrator";
		enable-gpios = <&pio 3 2 GPIO_ACTIVE_HIGH>; /* PD2 */
		vcc-supply = <&reg_dcdc1>;
	};
};

&codec {
	pinctrl-names = "default";
	pinctrl-0 = <&aif3_pins>;
	status = "okay";
};

&codec_analog {
	cpvdd-supply = <&reg_eldo1>;
	status = "okay";
};

&cpu0 {
	cpu-supply = <&reg_dcdc2>;
};

&cpu1 {
	cpu-supply = <&reg_dcdc2>;
};

&cpu2 {
	cpu-supply = <&reg_dcdc2>;
};

&cpu3 {
	cpu-supply = <&reg_dcdc2>;
};

&dai {
	status = "okay";
};

&de {
	status = "okay";
};

&dphy {
	status = "okay";
};

&dsi {
	vcc-dsi-supply = <&reg_dldo1>;
	status = "okay";

	panel@0 {
		compatible = "xingbangda,xbd599";
		reg = <0>;
		reset-gpios = <&pio 3 23 GPIO_ACTIVE_LOW>; /* PD23 */
		iovcc-supply = <&reg_dldo2>;
		vcc-supply = <&reg_ldo_io0>;
		backlight = <&backlight>;
	};
};

&ehci0 {
	status = "okay";
};

&ehci1 {
	status = "okay";
};

&i2c0 {
	status = "okay";

	touchscreen@5d {
		compatible = "goodix,gt917s";
		reg = <0x5d>;
		interrupt-parent = <&pio>;
		interrupts = <7 4 IRQ_TYPE_LEVEL_HIGH>; /* PH4 */
		irq-gpios = <&pio 7 4 GPIO_ACTIVE_HIGH>; /* PH4 */
		reset-gpios = <&pio 7 11 GPIO_ACTIVE_HIGH>; /* PH11 */
		AVDD28-supply = <&reg_ldo_io0>;
		VDDIO-supply = <&reg_ldo_io0>;
		touchscreen-size-x = <720>;
		touchscreen-size-y = <1440>;
	};
};

&i2c1 {
	status = "okay";

	/* Magnetometer */
	lis3mdl: magnetometer@1e {
		compatible = "st,lis3mdl-magn";
		reg = <0x1e>;
		vdd-supply = <&reg_dldo1>;
		vddio-supply = <&reg_dldo1>;
	};

	/* Light/proximity sensor */
	light-sensor@48 {
		compatible = "sensortek,stk3311";
		reg = <0x48>;
		interrupt-parent = <&pio>;
		interrupts = <1 0 IRQ_TYPE_EDGE_FALLING>; /* PB0 */
	};

	/* Accelerometer/gyroscope */
	accelerometer@68 {
		compatible = "invensense,mpu6050";
		reg = <0x68>;
		interrupt-parent = <&pio>;
		interrupts = <7 5 IRQ_TYPE_EDGE_RISING>; /* PH5 */
		vdd-supply = <&reg_dldo1>;
		vddio-supply = <&reg_dldo1>;
	};
};

/* Connected to pogo pins (external spring based pinheader for user addons) */
&i2c2 {
	status = "okay";
};

&lradc {
	vref-supply = <&reg_aldo3>;
	wakeup-source;
	status = "okay";

	button-200 {
		label = "Volume Up";
		linux,code = <KEY_VOLUMEUP>;
		channel = <0>;
		voltage = <200000>;
	};

	button-400 {
		label = "Volume Down";
		linux,code = <KEY_VOLUMEDOWN>;
		channel = <0>;
		voltage = <400000>;
	};
};

&mmc0 {
	pinctrl-names = "default";
	pinctrl-0 = <&mmc0_pins>;
	vmmc-supply = <&reg_dcdc1>;
	vqmmc-supply = <&reg_dcdc1>;
	cd-gpios = <&pio 5 6 GPIO_ACTIVE_LOW>; /* PF6 */
	disable-wp;
	bus-width = <4>;
	status = "okay";
};

&mmc1 {
	pinctrl-names = "default";
	pinctrl-0 = <&mmc1_pins>;
	vmmc-supply = <&reg_vbat_wifi>;
	vqmmc-supply = <&reg_dldo4>;
	bus-width = <4>;
	non-removable;
	status = "okay";

	rtl8723cs: wifi@1 {
		reg = <1>;
	};
};

&mmc2 {
	pinctrl-names = "default";
	pinctrl-0 = <&mmc2_pins>;
	vmmc-supply = <&reg_dcdc1>;
	vqmmc-supply = <&reg_dcdc1>;
	bus-width = <8>;
	non-removable;
	cap-mmc-hw-reset;
	status = "okay";
};

&ohci0 {
	status = "okay";
};

&ohci1 {
	status = "okay";
};

&pio {
	vcc-pb-supply = <&reg_dcdc1>;
	vcc-pc-supply = <&reg_dcdc1>;
	vcc-pd-supply = <&reg_dcdc1>;
	vcc-pe-supply = <&reg_aldo1>;
	vcc-pf-supply = <&reg_dcdc1>;
	vcc-pg-supply = <&reg_dldo4>;
	vcc-ph-supply = <&reg_dcdc1>;
};

&r_pio {
	/*
	 * FIXME: We can't add that supply for now since it would
	 * create a circular dependency between pinctrl, the regulator
	 * and the RSB Bus.
	 *
	 * vcc-pl-supply = <&reg_aldo2>;
	 */
};

&r_pwm {
	status = "okay";
};

&r_rsb {
	status = "okay";

	axp803: pmic@3a3 {
		compatible = "x-powers,axp803";
		reg = <0x3a3>;
		interrupt-parent = <&r_intc>;
		interrupts = <GIC_SPI 32 IRQ_TYPE_LEVEL_LOW>;
	};
};

#include "axp803.dtsi"

&battery_power_supply {
	status = "okay";
};

&reg_aldo1 {
	regulator-min-microvolt = <1800000>;
	regulator-max-microvolt = <1800000>;
	regulator-name = "dovdd-csi";
};

&reg_aldo2 {
	regulator-always-on;
	regulator-min-microvolt = <1800000>;
	regulator-max-microvolt = <1800000>;
	regulator-name = "vcc-pl";
};

&reg_aldo3 {
	regulator-always-on;
	regulator-min-microvolt = <3000000>;
	regulator-max-microvolt = <3000000>;
	regulator-name = "vcc-pll-avcc";
};

&reg_dcdc1 {
	regulator-always-on;
	regulator-min-microvolt = <3300000>;
	regulator-max-microvolt = <3300000>;
	regulator-name = "vcc-3v3";
};

&reg_dcdc2 {
	regulator-always-on;
	regulator-min-microvolt = <1000000>;
	regulator-max-microvolt = <1300000>;
	regulator-name = "vdd-cpux";
};

/* DCDC3 is polyphased with DCDC2 */

&reg_dcdc5 {
	regulator-always-on;
	regulator-min-microvolt = <1200000>;
	regulator-max-microvolt = <1200000>;
	regulator-name = "vcc-dram";
};

&reg_dcdc6 {
	regulator-always-on;
	regulator-min-microvolt = <1100000>;
	regulator-max-microvolt = <1100000>;
	regulator-name = "vdd-sys";
};

&reg_dldo1 {
	regulator-min-microvolt = <3300000>;
	regulator-max-microvolt = <3300000>;
	regulator-name = "vcc-dsi-sensor";
};

&reg_dldo2 {
	regulator-min-microvolt = <1800000>;
	regulator-max-microvolt = <1800000>;
	regulator-name = "vcc-mipi-io";
};

&reg_dldo3 {
	regulator-min-microvolt = <2800000>;
	regulator-max-microvolt = <2800000>;
	regulator-name = "avdd-csi";
};

&reg_dldo4 {
	regulator-min-microvolt = <1800000>;
	regulator-max-microvolt = <1800000>;
	regulator-name = "vcc-wifi-io";
};

&reg_eldo1 {
	regulator-always-on;
	regulator-min-microvolt = <1800000>;
	regulator-max-microvolt = <1800000>;
	regulator-name = "vcc-lpddr";
};

&reg_eldo3 {
	regulator-min-microvolt = <1800000>;
	regulator-max-microvolt = <1800000>;
	regulator-name = "dvdd-1v8-csi";
};

&reg_fldo1 {
	regulator-min-microvolt = <1200000>;
	regulator-max-microvolt = <1200000>;
	regulator-name = "vcc-1v2-hsic";
};

&reg_fldo2 {
	regulator-always-on;
	regulator-min-microvolt = <1100000>;
	regulator-max-microvolt = <1100000>;
	regulator-name = "vdd-cpus";
};

&reg_ldo_io0 {
	regulator-min-microvolt = <3300000>;
	regulator-max-microvolt = <3300000>;
	regulator-name = "vcc-lcd-ctp-stk";
	status = "okay";
};

&reg_ldo_io1 {
	regulator-min-microvolt = <1800000>;
	regulator-max-microvolt = <1800000>;
	regulator-name = "vcc-1v8-typec";
	status = "okay";
};

&reg_rtc_ldo {
	regulator-name = "vcc-rtc";
};

&sound {
	status = "okay";
	simple-audio-card,name = "PinePhone";
	simple-audio-card,aux-devs = <&codec_analog>, <&speaker_amp>;
	simple-audio-card,widgets = "Microphone", "Headset Microphone",
				    "Microphone", "Internal Microphone",
				    "Headphone", "Headphone Jack",
				    "Speaker", "Internal Earpiece",
				    "Speaker", "Internal Speaker";
	simple-audio-card,routing =
			"Headphone Jack", "HP",
			"Internal Earpiece", "EARPIECE",
			"Internal Speaker", "Speaker Amp OUTL",
			"Internal Speaker", "Speaker Amp OUTR",
			"Speaker Amp INL", "LINEOUT",
			"Speaker Amp INR", "LINEOUT",
			"Left DAC", "DACL",
			"Right DAC", "DACR",
			"ADCL", "Left ADC",
			"ADCR", "Right ADC",
			"Internal Microphone", "MBIAS",
			"MIC1", "Internal Microphone",
			"Headset Microphone", "HBIAS",
			"MIC2", "Headset Microphone";

	simple-audio-card,dai-link@2 {
		format = "dsp_a";
		frame-master = <&link2_codec>;
		bitclock-master = <&link2_codec>;
		bitclock-inversion;

		link2_cpu: cpu {
			sound-dai = <&bt_sco_codec 0>;
		};

		link2_codec: codec {
			sound-dai = <&codec 2>;
			dai-tdm-slot-num = <1>;
			dai-tdm-slot-width = <32>;
		};
	};
};

&uart0 {
	pinctrl-names = "default";
	pinctrl-0 = <&uart0_pb_pins>;
	status = "okay";
};

&uart1 {
	pinctrl-names = "default";
	pinctrl-0 = <&uart1_pins>, <&uart1_rts_cts_pins>;
	status = "okay";

	bluetooth {
		compatible = "realtek,rtl8723cs-bt";
		device-wake-gpios = <&pio 7 6 GPIO_ACTIVE_LOW>; /* PH6 */
		enable-gpios = <&r_pio 0 4 GPIO_ACTIVE_HIGH>; /* PL4 */
		host-wake-gpios = <&r_pio 0 5 GPIO_ACTIVE_HIGH>; /* PL5 */
	};
};

/* Connected to the modem (hardware flow control can't be used) */
&uart3 {
	pinctrl-names = "default";
	pinctrl-0 = <&uart3_pins>;
	status = "okay";
};

&usb_otg {
	dr_mode = "peripheral";
	status = "okay";
};

&usb_power_supply {
	status = "okay";
};

&usbphy {
	status = "okay";
};