malloc

kernel malloc

在应用程序中获取内存通常使用函数malloc(),但在设备驱动程序中动态开辟内存可以以字节或页面为单位。其中,以字节为单位分配内存的函数有kmalloc(),注意的是,kmalloc()函数返回的是物理地址,而malloc()等返回的是线性虚拟地址,因此在驱动程序中不能使用malloc()函数。与malloc()不同,kmalloc()申请空间有大小限制。长度是2的整次方,并且不会对所获取的内存空间清零。
以页为单位分配内存的函数如下所示:

get_zeroed_page():获得一个已清零页面。
get_free_page():获得一个或几个连续页面。
get_dma_pages():获得用于DMA传输的页面。

与之相对应的释放内存用也有kfree()或free_page函数族。

头文件 #include
函数原型 void* kmalloc(unsigned int len,int flags)
len 希望申请的字节数
flags GFP_KERNEL 内核内存通常的分配方法,会引发睡眠
返回值 成功写入的数据长度,失败返回 -EFAULT

malloc 和 slab 的关联

:)

Systemd

System-V 其实指的就是通常的那种/etc/init.d/的方式。

SystemV 和 BSD 是两种Unix风格

Sytem V BSD
Root脚本位置 /etc/init.d /etc/rc.d
默认Shell Bshell Cshell
文件系统数据 /etc/mnttab /etc/mtab
内核位置 /UNIX /vmUnix
打印机设备 lp rlp
字符串函数 memcopy bcopy
终端初始化设置文件 /etc/initab /etc/ttys
终端控制 termio termios

通常的那些IPC方法(共享内存、消息队列、信号量)也是针对System V.

Systemd
System-V

Ubuntu账户管理

添加新账户并加入root组

sudo adduser ubuntu

sudo adduser ubuntu sudo

当前用户改名

当前用户处于登录状态

quectel@q-OptiPlex-7070:/home$ sudo su
root@q-OptiPlex-7070:/home# usermod -l VincentW -d /home/VincentW -m q
usermod: user q is currently used by process 1173


root@q-OptiPlex-7070:/home# ps -elf | grep 1173
4 S q           1173       1  0  80   0 -  5041 ep_pol 21:52 ?        00:00:00 /lib/systemd/systemd --user
5 S q           1174    1173  0  80   0 - 42414 do_sig 21:52 ?        00:00:00 (sd-pam)
0 S q           1179    1173  0  69 -11 - 203425 poll_s 21:52 ?       00:00:00 /usr/bin/pulseaudio --daemonize=no --log-target=journal
0 S q           1194    1173  0  80   0 -  2055 ep_pol 21:52 ?        00:00:00 /usr/bin/dbus-daemon --session --address=systemd: --nofork --nopidfile --systemd-activation --syslog-only
0 S q           1310    1173  0  80   0 - 76380 poll_s 21:52 ?        00:00:00 /usr/libexec/at-spi-bus-launcher
0 S q           1320    1173  0  80   0 - 40707 poll_s 21:52 ?        00:00:00 /usr/libexec/at-spi2-registryd --use-gnome-session
0 S q           1363    1173  0  80   0 - 60731 poll_s 21:52 ?        00:00:00 /usr/libexec/gvfsd
0 S q           1503    1173  0  80   0 - 94584 futex_ 21:52 ?        00:00:00 /usr/libexec/gvfsd-fuse /run/user/1000/gvfs -f -o big_writes
0 S q           1506    1173  0  80   0 - 79312 poll_s 21:52 ?        00:00:00 /usr/libexec/gvfs-udisks2-volume-monitor
0 S q           1547    1173  0  80   0 - 59771 poll_s 21:52 ?        00:00:00 /usr/libexec/gvfs-goa-volume-monitor
0 S q           1566    1173  0  80   0 - 79984 poll_s 21:52 ?        00:00:00 /usr/libexec/gvfs-afc-volume-monitor
0 S q           1571    1173  0  80   0 - 60289 poll_s 21:52 ?        00:00:00 /usr/libexec/gvfs-gphoto2-volume-monitor
0 S q           1576    1173  0  80   0 - 59720 poll_s 21:52 ?        00:00:00 /usr/libexec/gvfs-mtp-volume-monitor
0 S q           1588    1173  0  80   0 - 68733 poll_s 21:52 ?        00:00:00 /usr/lib/x86_64-linux-gnu/bamf/bamfdaemon
0 S q           1625    1173  0  80   0 - 39089 poll_s 21:52 ?        00:00:00 /usr/libexec/dconf-service
0 S q           1712    1173  0  80   0 - 10996 poll_s 21:53 ?        00:00:00 /usr/lib/bluetooth/obexd
0 S q           1721    1173  0  80   0 - 117834 poll_s 21:53 ?       00:00:00 /usr/lib/x86_64-linux-gnu/libexec/kactivitymanagerd
0 S q           1729    1173  0  80   0 - 59106 poll_s 21:53 ?        00:00:00 /usr/bin/kglobalaccel5
0 S q           1732    1173  0  80   0 - 41338 poll_s 21:53 ?        00:00:00 /usr/libexec/gvfsd-metadata
0 S q           1888    1173  0  80   0 - 56808 poll_s 21:55 ?        00:00:00 /usr/sbin/kylinssoclient

因此还是要在recovery mode下修改。

/etc/passwd 和 /etc/shadow 替换

Ubuntu

和Debian、Raspberry Pi系统没什么本质区别。问题是

debian 文件系统如何搭建
如何构建一个完整的Ubuntu系统的SDK或者源码

debootstrap

什么是FHS?

What to do?

1
2
3
4
5
6
7

sudo apt-get install debootstrap

sudo debootstrap --arch [平台] [发行版本代号] [目录]

for example: sudo debootstrap --arch i386 trusty /mnt

On Fedora, there is febootstrap.

利用debootstrap构建一个可单独运行的镜像文件。



title: Ubuntu 64位机器上运行32位程序

10.04之后系统是

$ sudo apt-get install lib32z1
$ sudo apt-get install libc6:i386 libncurses5:i386 libstdc++6:i386

AndroidBsp

=====

RIL

Android RIL的Java 框架

java部分
RIL模
Phone模块

Lineage OS on RP3B

参考

LineageOS 17.1 (Android 10) for Raspberry Pi 3

LineageOS 17.1 (Android 10) for for Raspberry Pi 4

Ubuntu下为树莓派3B编译Android(Lineage OS)7.1.2系统

repo init -u git://github.com/LineageOS/android.git -b cm-14.1

curl --create-dirs -L -o .repo/local_manifests/manifest_brcm_rpi3.xml -O -L https://raw.githubusercontent.com/lineage-rpi/android_local_manifest/cm-14.1/manifest_brcm_rpi3.xml

repo sync

编译kernel

source build/envsetup.sh
lunch lineage_rpi3-userdebug
make ramdisk systemimage

分区1 128MB 分配给 BOOT : 用 fdisk : W95 FAT32(LBA) & Bootable, mkfs.vfat
分区2 1024MB 分配给 /system : 用 fdisk, 新建主分区
分区3 分配给 /data : 用 fdisk, mkfs.ex4

七、写入编译好的文件
1.写入系统分区

假设system分区挂载在/dev/sdb2下:

$ cd out/target/product/rpi3
$ sudo dd if=system.img of=/dev/sdb2 bs=1M

2.复制内核文件到boot分区

  • 复制device/brcm/rpi3/boot/* 到 分区1:/
  • 复制kernel/rpi/arch/arm/boot/zImage 到 分区1:/
  • 复制kernel/rpi/arch/arm/boot/dts/bcm2710-rpi-3-b.dtb 到 分区1:/
  • 复制kernel/rpi/arch/arm/boot/dts/overlays/vc4-kms-v3d.dtbo 到 分区1:/overlays/vc4-kms-v3d.dtbo
  • 复制out/target/product/rpi3/ramdisk.img 到 分区1:/

还没尝试!!!

Android

:)

Khadas

=====

Web

DOCs

KVim3

Github

Forum

Android

总之

下载:

  • repo 的REPO_URL和default.xml 的aosp的地址,改成清华的;
  • repo start branch –all //branch 选 khadas-vims-pie

编译:

  • 先编译uboot

  • 网上找Android编译需要的环境,可以解决所有问题

  • target是 out目录里update.img,1G大小不到

    $ cd PATH_YOUR_PROJECT
    $ cd bootloader/uboot
    $ ./mk TARGET //kvim3
    $ cd PATH_YOUR_PROJECT
    $ source build/envsetup.sh
    $ lunch TARGET_LUNCH //kvim3-userdebug
    $ make -jN otapackage


repo 工具

export REPO_URL='https://mirrors.tuna.tsinghua.edu.cn/git/git-repo'

官方推荐的是按照Android

repo init -u https://github.com/khadas/android_manifest.git -b khadas-vims-pie

实际上不可行。因为国内访问不了谷歌。AOSP无法下载。

办法是修改.repo/manifests/default.xml,按照清华大学镜像网站的方法

清华大学 Android 镜像使用帮助

https://android.googlesource.com/ 全部使用 https://mirrors.tuna.tsinghua.edu.cn/git/AOSP/ 代替即可。

但是,由于直接修改xml会导致第一次repo sync失败后第二次失败。将https://github.com/khadas/android_manifest.git fork一份到自己的github空间,并修改khadas-vims-pi分支对应的default.script

后续尝试,可以直接使用自己的git仓库里的

repo init -u https://github.com/MrVW/android_manifest.git -b khadas-vims-pie

防止sync 失败,失败后不断重试

#!/bin/bash   


repo sync   -j1 --fail-fast
while [ $? = 1 ]; do   
        echo "================sync failed, re-sync again ====="   
    sleep 3   
    repo sync   -j1 --fail-fast
done

$?:获取函数返回值或者上一个命令的退出状态

Ubuntu

:)

使用qemu搭建ARM Vexpress嵌入式linux开发环境

============

在arm开发板上成功运行Linux系统,我们有如下三个方面的任务:

制作bootloader;
编译linux内核、linux内核模块、linux设备树;
制作根文件系统。

我们使用qemu虚拟机来上手嵌入式linux的开发。

安装qemu与arm交叉编译工具

Linux内核与设备树编译

下载Linux内核:https://www.kernel.org/

git clone https://mirrors.tuna.tsinghua.edu.cn/git/linux.git

https://mirror.bjtu.edu.cn/kernel/linux/kernel/


make vexpress_defconfig

make zImage 

make modules

make dtbs

得到zImage、dtb

尝试启动

qemu-system-arm -M vexpress-a9 -m 512M -kernel arch/arm/boot/zImage -dtb arch/arm/boot/dts/vexpress-v2p-ca9.dtb -nographic -append "console=ttyAMA0"

看到

rtc-pl031 10017000.rtc: setting system clock to 2020-11-02 09:39:39 UTC (1604309979)
ALSA device list:
  #0: ARM AC'97 Interface PL041 rev0 at 0x10004000, irq 33
input: ImExPS/2 Generic Explorer Mouse as /devices/platform/smb/smb:motherboard/smb:motherboard:iofpga@7,00000000/10007000.kmi/serio1/input/input2
VFS: Cannot open root device "(null)" or unknown-block(0,0): error -6
Please append a correct "root=" boot option; here are the available partitions:
1f00          131072 mtdblock0  (driver?)
1f01           32768 mtdblock1  (driver?)
Kernel panic - not syncing: VFS: Unable to mount root fs on unknown-block(0,0)
CPU: 0 PID: 1 Comm: swapper/0 Not tainted 4.4.99 #1
Hardware name: ARM-Versatile Express
[<80016454>] (unwind_backtrace) from [<80012ee0>] (show_stack+0x10/0x14)
[<80012ee0>] (show_stack) from [<80243aac>] (dump_stack+0x94/0xa8)
[<80243aac>] (dump_stack) from [<800a5638>] (panic+0x9c/0x200)
[<800a5638>] (panic) from [<8062f250>] (mount_block_root+0x1c0/0x25c)
[<8062f250>] (mount_block_root) from [<8062f408>] (mount_root+0x11c/0x124)
[<8062f408>] (mount_root) from [<8062f568>] (prepare_namespace+0x158/0x1a0)
[<8062f568>] (prepare_namespace) from [<8062eeec>] (kernel_init_freeable+0x268/0x278)
[<8062eeec>] (kernel_init_freeable) from [<804a440c>] (kernel_init+0x8/0xe8)
[<804a440c>] (kernel_init) from [<8000f4f8>] (ret_from_fork+0x14/0x3c)
---[ end Kernel panic - not syncing: VFS: Unable to mount root fs on unknown-block(0,0)

busybox

https://busybox.net/downloads/

编译生成一个 __install 文件夹

制作根文件系统

mkdir rootfs

将_install 目录里的内容拷贝到rootfs目录中

新建目录 mkdir lib

将arm交叉编译器的库复制过来:cp -r /usr/arm-linux-gnueabi/lib/* lib/

在rootfs目录下新建目录mkdir dev/,进入该目录cd dev/,创建节点sudo mknod -m 666 tty1 c 4 1(串口字符设备,主设备号为4,从设备号为1)

重复创建多个串口设备,注意分配好从设备号:

创建一个控制台节点:mknod -m 666 console c 5 1

创建一个空节点:mknod -m 666 null c 1 3

回到home目录,输入命令dd if=/dev/zero of=rootfs.ext3 bs=1M count=32生成虚拟SD卡系统镜像,可以得到一个rootfs.ext3文件。
格式化该镜像:mkfs.ext3 rootfs.ext3
挂载该镜像到本地:mount -t ext3 rootfs.ext3 /mnt -o loop

将之前准备的rootfs目录下的所有文件都拷贝到该镜像挂载点:cp -r /home/zvcv/rootfs/* /mnt/

卸载:umount /mnt/
进入linux源码目录: cd linux/

使用qemu启动内核:qemu-system-arm -M vexpress-a9 -m 512M -kernel arch/arm/boot/zImage -dtb arch/arm/boot/dts/vexpress-v2p-ca9.dtb -nographic -append “root=/dev/mmcblk0 rw console=ttyAMA0” -sd /home/zvcv/rootfs.ext3,这里比之前多指定了一个sd镜像。

点击回车,进入命令行,linux启动完毕。

我遇到了无法启动,原因是内核编译选项选的是ext4 ,所以格式化的时候选mkfs.ext4

uboot

https://ftp.denx.de/pub/u-boot/

不要用最新版本

scripts/kconfig/conf  --syncconfig Kconfig
  UPD     include/config.h
  GEN     include/autoconf.mk.dep
  CFG     u-boot.cfg
  GEN     include/autoconf.mk
  UPD     include/generated/dt.h
  UPD     include/generated/timestamp_autogenerated.h
  UPD     include/config/uboot.release
*** Your GCC is older than 6.0 and is not supported
arch/arm/config.mk:66: recipe for target 'checkgcc6' failed
make: *** [checkgcc6] Error 1

我的arm-linux-gnuebi-gcc 是5.5

换2015年的uboot才能build pass

NFS

sudo apt-get install uml-utilities bridge-utils

cd linux-4.4.232/

make LOADADDR=0x60003000 uImage -j4

mkimage command not found U-Boot images will not be built —>

sudo apt-get install u-boot-tools

sudo apt-get install tftp-hpa tftpd-hpa xinetd

u-boot 要能加载uImage,需要修改

默认的bootcmd,变成tftp加载tftp server上的uImage

vim include/configs/vexpress_common.h

注释默认的 CONFIG_BOOTCOMMAND

添加

#define CONFIG_BOOTCOMMAND  "tftp 0x60003000 uImage; setenv bootargs'root=/dev/mmcblk0 console=ttyAMA0'; bootm 0x60003000"

另外一个说法是

#define CONFIG_BOOTCOMMAND  "tftp 0x60003000 uImage; tftp 0x60500000 vexpress-v2p-ca9.dtb; setenv bootargs 'root=/dev/mmcblk0 console=ttyAMA0'; bootm 0x60003000 - 0x60500000"

可以配置IP和netmask

#define CONFIG_IPADDR   192.168.1.49
#define CONFIG_NETMASK  255.255.255.0
#define CONFIG_SERVERIP 192.168.1.88

在Quectel的台式机虚拟机里的桥接网卡,实际配置成

#define CONFIG_IPADDR   192.168.1.49
#define CONFIG_NETMASK  255.255.254.0
#define CONFIG_SERVERIP 10.66.83.84

QEMU和主机如何ping通

在Ubuntu下使用QEMU连网
https://blog.csdn.net/yang1111111112/article/details/107811796

写一个脚本

if test -z $1 ; then
    echo need a argument: down/up
    exit
fi 

if [ "up" = $1  ] ; then
    # 新建一个网桥,名称为br0
    brctl addbr br0
    # 将网络设备enp0s10添加到网桥br0 
    ifconfig enp0s9 down
    brctl addif br0 enp0s9

    # 关闭生成树协议
    brctl stp br0 off

    ifconfig br0 192.168.1.1 netmask 255.255.255.0 promisc up
    ifconfig enp0s9 192.168.1.88 netmask 255.255.255.0 promisc up


     # 使用命令tunctl添加虚拟网卡tap
    tunctl -t tap0 -u rlk

    ifconfig tap0 192.168.1.89 netmask 255.255.255.0 promisc up

    brctl addif br0 tap0

else
    ifconfig tap0 down
    brctl delif br0 tap0

    ifconfig enp0s9 down
    brctl delif br0 enp0s9
    ifconfig br0 down
    brctl delbr br0

    ifconfig enp0s9 192.168.1.88 netmask 255.255.255.0
fi

其中enp0s9是VirtualBox里的一个Host Only添加的网卡。

生成的这个tap0 就是serverip
在qemu中可以ping 通该IP

sudo qemu-system-arm -M vexpress-a9 -m 1024M -kernel u-boot -dtb /home/rlk/QEMU/tftpboot/vexpress-v2p-ca9.dtb  -nographic -net nic,macaddr=52:54:00:12:34:22 -net tap,ifname=tap0 -sd  vexpress.ext3

在uboot里,
setenv serverip xxx
setenv ipaddr xxx
ping ${serverip}

网络能ping通的情况下

tftp 0x60003000 uImage
setenv bootargs ‘root=/dev/mmcblk0 console=ttyAMA0’
bootm 0x60003000

NFS

RT Thread

Ubuntu 平台开发RT-Thread

qemu 模拟 ARM 从sd卡启动 uboot 内核

http://www.vjiot.net/typecho/index.php/archives/58/

:)

Android 10 On IMX8

======

Source Code from

https://pan.baidu.com/s/1ldI06aZYT1E2BrBoba7Dqg 提取码

编译环境 2021.1.14

参考

OKMX8MM-C(Android)用户资料-20200302\原厂资料\Android_User’s_Guide.pdf

OKMX8MM-C(Android)用户资料-20200302\原厂资料\Android_Quick_Start_Guide.pdf

OKMX8MM-C(Android)用户资料-20200302\手册\OKMX8MM-C_Android_用户手册_V1.1_2020.03.02.pdf

Ubuntu 环境

官方文档要求 Ubuntu 16.04 X64

$ sudo add-apt-repository ppa:openjdk-r/ppa 
$ sudo apt-get update 
$ sudo apt-get install uuid \ 
uuid-dev \ 
zlib1g-dev \ 
liblz-dev \ 
liblzo2-2 \ 
liblzo2-dev \ 
lzop \ 
git-core curl \ 
u-boot-tools \ 
mtd-utils \ 
android-tools-fsutils \ 
openjdk-8-jdk \ 
device-tree-compiler \ 
gdisk \ 
m4 \ 
libz-dev

jdk 要求是1.8版本

解压源码

$ cd /home/forlinx/imx8mm/ 
$cat OK8MM-android-source.tar.bz2_a* > OK8MM-android-source.tar.bz2 
$ tar -xvf OK8MM-android-source.tar.bz2 

自定义docker环境

按照Ubuntu 环境,自定义docker环境,并且支持ssh 登录docker 容器中的ubuntu

已经上传到docker.io

下载

docker pull quectel/imx8_android9:latest

用户名 imx8 密码 quectel123

编译Android

运行docker 环境

android@q-OptiPlex-7070:~$ docker run -d --name imx8 -v /home/android/IMX8_Android9:/home/imx8/imx8_Android -v /etc/localtime:/etc/localtime:ro   -v
 /etc/timezone:/etc/timezone:ro --device=/dev/loop-control:/dev/loop-control --device=/dev/loop0:/dev/loop0 --cap-add SYS_ADMIN -p 6666:22  --privil
eged  ubuntu:16_jdk1.8  /usr/sbin/sshd -D
57c2bf9c7ccefaa4701f006c420d3d5ededfdf3f0ea0b0655772d42c21b566e7
android@q-OptiPlex-7070:~$
android@q-OptiPlex-7070:~$
android@q-OptiPlex-7070:~$ docker ps
CONTAINER ID   IMAGE              COMMAND               CREATED         STATUS         PORTS                  NAMES
57c2bf9c7cce   ubuntu:16_jdk1.8   "/usr/sbin/sshd -D"   6 seconds ago   Up 3 seconds   0.0.0.0:6666->22/tcp   imx8
android@q-OptiPlex-7070:~$ ls
模板  camdroid  IMX8_Android9  Khadas  Tiny4412_android5.1  v3s_camdroid.zip

SSH远程连接到

ssh -P 6666 ${HOST_IP}

PS D:\BaiduNetdiskDownload\imx8-android> ssh -p 6666 imx8@10.66.83.84
The authenticity of host '[10.66.83.84]:6666 ([10.66.83.84]:6666)' can't be established.
ECDSA key fingerprint is SHA256:vhkbWtZEDaEjXzh6phneA4VSDB3hLSZdvOr8ZD/zYvw.
Are you sure you want to continue connecting (yes/no)? yes
Warning: Permanently added '[10.66.83.84]:6666' (ECDSA) to the list of known hosts.
imx8@10.66.83.84's password:
Welcome to Ubuntu 16.04.7 LTS (GNU/Linux 5.4.0-58-generic x86_64)

在docker容器中编译

$ cd /home/imx8/imx8_Android/OK8MM-android-source 
$ source build/envsetup.sh 
$ lunch evk_8mm-userdebug
$ make -j8

Notes

export JAVA_TOOL_OPTIONS=-Dfile.encoding=UTF8

内核驱动移植

vi out/target/product/evk_8mm/obj/KERNEL_OBJ/.config vendor/nxp-opensource/kernel_imx/arch/arm64/configs/android_defconfig -O

(或者vimdiff)

判断得知内核的配置文件是

OK8MM-android-source/vendor/nxp-opensource/kernel_imx/arch/arm64/configs/android_defconfig

从结果看,已经将Quectel模组的VID、PID加到option.c中,并且移植了GobiNet驱动和qmi_wwan驱动。使用 EC2X 模组没有问题。

qmi_wwan 已经 build-in 编译

RIL库移植

/vendor/lib/libreference-ril.so
/vendor/lib64/libreference-ril.so


device/fsl/imx8m/evk_8mm/evk_8mm.mk:52:    device/fsl/imx8m/evk_8mm/lib/libreference-ril.so:$(TARGET_COPY_OUT_VENDOR)/lib64/libreference-ril.so 

烧录

在Linux上烧录,用root账户,否则/tmp/目录没法写。

uuu_imx_android_flash.bat -f imx8mm -e -c 7

uuu.exe 放到环境变量路径中;管理员权限执行

分区表

分区索引 名称 偏移 大小 文件系统 内容
NA Bootloader 33KB 4MB NA bootloader
1 dtbo_a 8MB 4MB NA dtbo.img
2 dtbo_b Follow dtbo_a 4MB NA dtbo.img
3 boot_a Follow dtbo_b 48MB boot.img(kernel+ramdisk) boot.img
4 boot_b Follow boot_a 48MB boot.img(kernel+ramdisk) boot.img
5 system_a Follow boot_b 1536MB ext4 挂载在 /system Android系统文件/system目录
6 system_b Follow system_a 1536MB ext4 挂载在 /system Android系统文件/system目录
7 misc Follow system_b 4MB NA 为了恢复保存bootloader信息
8 metadata Follow misc 2MB NA For system slide show
9 presistdata Follow metadata 1MB NA Option to operate unlock metadata
10 vendor_a Follow presistdata 256MB ext4.挂载在/vendor vendor.img
11 vendor_b Follow vendor_a 256MB ext4.挂载在/vendor vendor.img
12 userdata Follow vendor_b 剩余全部 ext4.挂载在/data 应用程序数据
13 fbmisc Follow userdata 1MB NA 保存lock/unlock状态
14 vbmeta_a Follow fbmisc 1MB NA 保存verify boot’s metadata
15 vbmeta_b Follow vbmeta_a 1MB NA 保存verify boot’s metadata

fastboot

关闭 DM 验证

设置-》系统-》开发者选项-》OEM 解锁 

在uboot阶段

fastboot 0

烧录vbmeta.img

fastboot oem unlock
fastboot --disable-verity flash vbmeta vbmeta.img

然后就可以直接用fastboot烧录了

fastboot flash system_a system.img

OTA

编译遇到的问题

[Q] error: unmappable character for encoding ASCII (java编译过程中出现的错误)

[A]

export JAVA_TOOL_OPTIONS=-Dfile.encoding=UTF8

[Q]Device is locked. Please unlock the device first

[A]开发者模式解锁

[Q]

[A]

Android FAQs

**[Q]客户移植RIL驱动,发现有两个rild

[A]**kill掉其中一个

[Q]hidl

[A]

[Q]Android 怎么改router,修改默认DNS
[A]

**[Q]**Android 怎么修改网卡的优先顺序


[A]

[Q] 海外的板子寄回国发现图标显示不对


[A] frameworks/base/services/core/java/com/android/server/connectivity/NetworkMonitor.java

    // Default configuration values for captive portal detection probes.
    // TODO: append a random length parameter to the default HTTPS url.
    // TODO: randomize browser version ids in the default User-Agent String.
    private static final String DEFAULT_HTTPS_URL     = "https://www.google.com/generate_204";
    private static final String DEFAULT_HTTP_URL      =
        "http://connectivitycheck.gstatic.com/generate_204";
    private static final String DEFAULT_FALLBACK_URL  = "http://www.google.com/gen_204";
    private static final String DEFAULT_OTHER_FALLBACK_URLS =
        "http://play.googleapis.com/generate_204";
    private static final String DEFAULT_USER_AGENT    = "Mozilla/5.0 (X11; Linux x86_64) "
                              + "AppleWebKit/537.36 (KHTML, like Gecko) "
                              + "Chrome/52.0.2743.82 Safari/537.36";

NetworkMonitor.java

[Q] 以太网和4G网卡共存


[A]
— a/services/core/java/com/android/server/ConnectivityService.java
+++ b/services/core/java/com/android/server/ConnectivityService.java
@@ -4247,7 +4248,8 @@ public class ConnectivityService extends IConnectivityManager.Stub
loge(“Dead network still had at least “ + nr);
break;
}
- nai.asyncChannel.disconnect();
+ log(“don’t teardownUnneededNetwork “ + nai);
+ //nai.asyncChannel.disconnect();
}

     private void handleLingerComplete(NetworkAgentInfo oldNetwork) {

[Q]


[A]

[Q]


[A]