前言

由于下载的开源系统没有系统签名,所以不可能针对系统去做什么定制。
首先,要去下载 Android-x86-6.0 的系统源码,再去尝试编译系统,如果编译成功并且能够正常运行的话,才能研究去定制系统。反正吧,我觉得编译系统是定制系统的第一步。不多说了,先去下载系统源码吧!

安装 Git

由于 Mac 自带 Git 工具,就不介绍如何安装,可以考虑升级 Git 版本

使用 repo 工具下载源码时会要求设置用户名和邮箱,如果你使用过 Git,应该早就设置过

git config --global user.name "your name"
git config --global user.email "XXX@XXX.com"

安装 Repo

官方是通过 Repo 管理 Android-x86 的源代码,所以我们要先安装 Repo 工具。安装步骤如下:

1.在根目录下创建 bin 文件夹

mkdir ~/bin

2.配置系统环境变量(可临时配置)

vi ~/.bash_profile
添加 export PATH=~/bin:$PATH

3.下载 repo(自备梯子,翻墙)

git clone https://gerrit.googlesource.com/git-repo

4.将 git-repo 中的 repo 文件拷贝到 ~/bin 目录中

cd git-repo
cp repo ~/bin/

5.修改权限

chmod a+x ~/bin/repo

至此,repo 工具安装配置完成

下载 Android-x86-6.0 源代码

目前国内并没有提供 Android-x86 源代码的仓库,所以下载源码需要翻墙,请大家自备梯子。

创建 Android-x86-6.0 文件夹

mkdir ~/Android-x86-6.0

初始化仓库

From git://git.osdn.net/gitroot/android-x86/manifest* [new branch]      android-x86-1.6    -> origin/android-x86-1.6* [new branch]      android-x86-2.2    -> origin/android-x86-2.2* [new branch]      android-x86-2.2-r2 -> origin/android-x86-2.2-r2* [new branch]      android-x86-4.0-r1 -> origin/android-x86-4.0-r1* [new branch]      android-x86-4.4-r1 -> origin/android-x86-4.4-r1* [new branch]      android-x86-4.4-r2 -> origin/android-x86-4.4-r2* [new branch]      android-x86-4.4-r3 -> origin/android-x86-4.4-r3* [new branch]      android-x86-4.4-r4 -> origin/android-x86-4.4-r4* [new branch]      android-x86-4.4-r5 -> origin/android-x86-4.4-r5* [new branch]      android-x86-6.0-r1 -> origin/android-x86-6.0-r1* [new branch]      android-x86-6.0-r2 -> origin/android-x86-6.0-r2* [new branch]      android-x86-6.0-r3 -> origin/android-x86-6.0-r3* [new branch]      android-x86-7.1-r1 -> origin/android-x86-7.1-r1* [new branch]      android-x86-7.1-r2 -> origin/android-x86-7.1-r2* [new branch]      cm-x86-14.1-r1     -> origin/cm-x86-14.1-r1* [new branch]      cm-x86-14.1-r2     -> origin/cm-x86-14.1-r2* [new branch]      cupcake-x86        -> origin/cupcake-x86* [new branch]      donut-x86          -> origin/donut-x86* [new branch]      eclair-x86         -> origin/eclair-x86* [new branch]      froyo-x86          -> origin/froyo-x86* [new branch]      gingerbread-x86    -> origin/gingerbread-x86* [new branch]      honeycomb-x86      -> origin/honeycomb-x86* [new branch]      ics-x86            -> origin/ics-x86* [new branch]      jb-x86             -> origin/jb-x86* [new branch]      kitkat-x86         -> origin/kitkat-x86* [new branch]      lollipop-x86       -> origin/lollipop-x86* [new branch]      marshmallow-x86    -> origin/marshmallow-x86* [new branch]      multiwindow-oreo   -> origin/multiwindow-oreo* [new branch]      nougat-x86         -> origin/nougat-x86* [new branch]      oreo-x86           -> origin/oreo-x86* [new branch]      pie-x86            -> origin/pie-x86

如上所示,官网使用不同的分支来维护不同的版本的 Android 源码, 这里我只下载有关 Android-x86-6.0 的源码,我选择的分支是 marshmallow-x86

cd ~/Android-x86-6.0
repo init -u git://git.osdn.net/gitroot/android-x86/manifest -b marshmallow-x86
// -b 指定分支,不指定分支会拉取所有分支源码

说明: 由于网络原因国内的访问不了 google 的仓库,所以上面的 repo 命令(一个 python 脚本封装了 git 的命令)中的 REPO_URL = 'https://gerrit.googlesource.com/git-repo’改为 REPO_URL = ‘git://git.omapzoom.org/git-repo.git’。

vi ~/bin/reporeplace
REPO_URL = 'https://gerrit.googlesource.com/git-repo'
to
REPO_URL = 'git://git.omapzoom.org/git-repo.git'

同步源码至本地

repo sync -f -j4 --no-tags --no-clone-bundle
// --no-tags:减少不需要的tag下载,可以缩减下载的代码量
// -f:当某个库因为网络原因货其他原因下载失败的时候可以继续进行,避免已经下载的代码不能写入到硬盘上
// -j4:开启4个线程来下载,这个根据CPU和硬盘的性能决定的

好了,让它慢慢下载吧。不出意外的话, 大概 3 小时左右就可以将 android-x86-6.0 的源码同步至本地。
如果意外中断的话,不用担心,使用该命令继续同步,直到成功为止。强烈建议多同步几次,一定要确保代码完全同步了,防止编译过程遇到找不到文件的错误

特意关注了 android-x86-6.0 的源码大小,15G 左右

搭建编译环境

由于我的 Mac Pro 配置难以支撑编译系统,所以申请了台服务器去编译系统。这里感谢公司的大力支持,为了编译系统和研究定制系统专门购买了服务器。关于如何查看服务器具体配置信息,请参考此篇文章Linux 下查看服务器配置

下面简单介绍下服务器的配置:

品牌 戴尔(DELL)
型号 PowerEdge R230
系统 Ubuntu 16.04.6 LTS 64 位
CPU 型号 Intel® Xeon® CPU E3-1220 v6 @ 3.00GHz
物理 CPU 个数 1
单个物理 CPU 核数 4 核
逻辑 CPU 的个数 4,即单个物理 CPU 核数 x 物理 CPU 个数
硬盘大小 1T
内存大小 8G

如上所示,是在 Ubuntu 16.04.5 LTS 系统上编译 Android-x86-6.0

硬件要求

1.编译 2.3.x 以上的版本要求 64 位的操作系统,2.3.x 以下的版本 32 位操作系统即可。

2.磁盘空间官方要求至少 100GB 以上,越大越好

软件要求

1.操作系统

官方是使用 Ubuntu 系统开发和测试的,这里同样使用 Ubuntu 系统编译

特别说明,不同的 Ubuntu 系统可以编译的 Android 版本

Android 版本 编译要求的 Ubuntu 最低版本
Android 6.0 至 AOSP master Ubuntu 14.04
Android 2.3.x 至 Android 5.x Ubuntu 12.04
Android 1.5 至 Android 2.2.x Ubuntu 10.0

2.JDK 版本

特别说明,编译不同 Android 版本的源码对应的 JDK 版本

Android 版本 编译要求的 JDK 版本
AOSP 的 Android 主线 OpenJDK 8
Android 5.x 至 android 6.0 OpenJDK 7
Android 2.3.x 至 Android 4.4.x Oracle JDK 6
Android 1.5 至 Android 2.2.x Oracle JDK 5

我现在编译的是 Android-x86-6.0 的系统,需要安装 OpenJDK 7。但是在 Ubuntu 15.04 及之后的版本的在线安装库中只支持 openjdk8 和 openjdk9 的安装,因此想要安装 openjdk 7 需要首先设置 ppa:

sudo add-apt-repository ppa:openjdk-r/ppa
sudo apt-get update

设置成功后,直接安装

sudo apt-get install openjdk-7-jdk

如果编译 android 6.0 以上版本,需要安装 openjdk8:

sudo apt-get update
sudo apt-get install openjdk-8-jdk

如果需要编译不同版本的 android 系统,需要切换不同的 jdk 版本:

sudo update-alternative --config java
sudo update-alternative --config javac

3.其它要求
这里就不介绍其它 Ubuntu 版本需要添加的依赖,如有需要参考Google 官方构建编译环境指南。下面是 Ubuntu16.04 需要添加的依赖:

sudo apt-get install -y libx11-dev:i386 libreadline6-dev:i386 libgl1-mesa-dev g++-multilib
sudo apt-get install -y git flex bison gperf build-essential libncurses5-dev:i386
sudo apt-get install -y tofrodos python-markdown libxml2-utils xsltproc zlib1g-dev:i386
sudo apt-get install -y dpkg-dev libsdl1.2-dev libesd0-dev
sudo apt-get install -y git-core gnupg flex bison gperf build-essential
sudo apt-get install -y zip curl zlib1g-dev gcc-multilib g++-multilib
sudo apt-get install -y libc6-dev-i386
sudo apt-get install -y lib32ncurses5-dev x11proto-core-dev libx11-dev
sudo apt-get install -y libgl1-mesa-dev libxml2-utils xsltproc unzip m4
sudo apt-get install -y lib32z-dev ccache

编译源码

由于 Android-x86-6.0 的源码我是下载至 Mac Pro 的,但是我要在 Ubuntu 服务器上编译,所以我要把源码上传到服务器。这里我直接使用scp命令进行文件传输:

scp -r ~/android-x86-6.0/ barry@192.168.1.52:/home/barry/

这样就直接将 android-x86-6.0 目录复制到 barry 目录下,现在源码传输也完成了

设置编译环境

切换到源码根目录下,执行以下命令:

source build/envsetup.sh

结果:

命令执行成功后,会得到一些常用的命令,像 lunch、mmm、mm 等。

选择编译目标

执行以下命令:

lunch

结果:

这里我直接选择对应的数字 10 或 android_x86_64-eng,编译 64 位的工程师版本。结果:

这样就选择好了需要编译的目标。

这里讲解下 lunch 命令,lunch 后面可以直接加参数,像lunch android_x86_64-eng这样,格式为lunch $TARGET_PRODUCT-$TARGET_BUILD_VARIANT

TARGET_PRODUCT

TARGET_PRODUCT 指的编译出的镜像搭载的运行环境,其中 aosp 代表 Android 的开源项目,arm 表示系统是运行在 arm 架构的处理器上,arm64 则是指 64 位 arm 架构处理器,x86 则表示 x86 架构的处理器。这里我们选择的 android_x86 就是指运行在 x86 架构处理器上。

TARGET_BUILD_VARIANT

TARGET_BUILD_VARIANT 指的是编译类型,一般是三种:

  • -user:代表编译的系统镜像是可以正式发布到市场的版本,权限被限制,像没有 root 权限、不能 debug 等
  • -userdebug:在 user 版本的基础上开放了 root 权限和 debug 权限
  • -eng:代表开发工程师的版本(engineer),拥有最大的权限(root 等),此外还附带了许多 debug 工具

开始编译

小提示

执行以下命令,指打开编译缓存,可以提高编译的效率

echo export USE_CCACHE=1 >> ~/.bashrcexport USE_CCACHE=1

编译指令

执行 make 指令进行代码编译:

make -j8 iso_img

-j 参数来设置参与编译的线程数量,以提高编译速度,这里我开启 8 个线程同时编译

ios_img 参数是直接将编译完成 android 系统打包成 iso 镜像,这样可以直接通过制作 U 盘启动安装在 X86 的 PC 机上

说明 参与编译的线程个数是根据你机器 cup 的核心来确定的:core*2,即当前 cpu 的核心的 2 倍.比如 Ubuntu 服务器是单核四线程,所以最快是启用 8 个线程去编译

建议 首次编译时最好不开启多线程编译,会导致某些报错信息被隐藏,难以定位编译错误

编译结果

如果编译过程中没有出现错误的话(我想这基本不可能),几个小时后就可以编译完成。如上图所示,当前你看 built successfully 此类信息,那么恭喜你编译成功了。

关于模块编译,使用mmmmm指令

mmm: 编译指定模块,需要传入模块路径,像mmm external/iptables这样

mm: 编译当前模块,即当前目录下的模块,不需要传入模块路径,像cd external && mm ./这样

运行系统

具体关于如何安装并且运行 Android-x86-6.0,请参考如何安装 x86-6.0

编译错误

说到编译过程真是一把辛酸泪,就遇到各种错误,乍一看你完全不知道怎么回事的。没办法只能 google,还好遇到错误的不止我一个,网上还是解决方案的。这里推荐下google 关于 android-x86 的论坛,上面可以找到很多有用的信息。

既然遇到了这么多错误,也就记录下来,既当作总结也方便其它人。

问题一描述

/usr/local/bin/make target-files-package -j4

Ubuntu16.04 中自带的 make 版本过高,导致无法识别源码中 Makefile 部分语法。 这里查看服务器的 make 版本为 4.1,需要降低 make 版本为 3.8.1

解决方案

  • 下载 make 3.8.1,并且解压
  • cd make 3.81,切换你的解压路径
  • ./configure
  • make
  • sudo make install

这样 make 降版本就成功了,使用make -v查看当前版本

问题二描述

In file included from out/target/product/x86/obj/STATIC_LIBRARIES/libext4_intermediates/libipt_ECN.c:11:0:
external/iptables/extensions/../include/linux/netfilter_ipv4/ipt_ECN.h:13:37: fatal error: linux/netfilter/xt_DSCP.h: No such file or directory#include <linux/netfilter/xt_DSCP.h>^
compilation terminated.

解决方案

应该是 Mac 的存储不区分大小写,导致下载的源码缺失文件,就将同名的小写文件拷贝一份就可以解决

cd external/iptables/extensions/../include/linux/netfilter
ln -s xt_dscp.h xt_DSCP.h

问题三描述

Error: out/target/common/obj/JAVA_LIBRARIES/framework_intermediates/classes.jar: unknown package name of class file org/android_x86/analytics/AnalyticsHelper$1.class

解决方案

vi build/core/tasks/check_boot_jars/package_whitelist.txt
末尾插入`org\.android_x86\.analytics`

问题四描述

make[4]: *** No rule to make target `net/netfilter/xt_TCPMSS.o', needed by `net/netfilter/built-in.o'.  Stop.
make[3]: *** [net/netfilter] Error 2
make[2]: *** [net] Error 2

解决方案

应该是 Mac 的存储不区分大小写,导致下载的源码缺失文件,就将同名的小写文件拷贝一份就可以解决

cd kernel/net/netfilter/
ln -s xt_tcpmss.c xt_TCPMSS.c

问题五描述

error: linux/netfilter/xt_TCPMSS.h: No such file or directory

解决方案

应该是 Mac 的存储不区分大小写,导致下载的源码缺失文件,就将同名的小写文件拷贝一份就可以解决

ls -s external/kernel-headers/original/uapi/linux/netfilter/xt_tcpmss.h external/iptables/include/linux/netfilter/xt_TCPMSS.h

问题六描述

sid_tables.h: No such file or directory

解决方案

这个问题非常诡异,我使用make单个线程编译一定会出现,当我使用make -j8多个线程编译的话就不会出现,真是辛酸阿。如果这样解决不了的话,请尝试下面的方法:

方式一:
cd ./external/mesa/src/amd/common
python sid_tables.py sid.h > sid_tables.h
cd external/mesa/src/intel/genxml/
python gen_pack_header.py gen*.xml > gen*_pack.h # *代表文件中gen的文件,都手动python执行方式二:
vi ./external/mesa/src/amd/Android.common.mk
line 41, add $(LOCAL_GENERATED_SOURCES): MESA_SID_TABLE_H := $(addprefix $(call local-generated-sources-dir)/, \common/sid_tables.h)
vi external/mesa/src/gallium/drivers/radeonsi/Android.mk
line 44, add LOCAL_GENERATED_SOURCES += $(MESA_SID_TABLE_H)

问题七描述

target StaticLib: libmesa_pipe_svga (out/target/product/x86/obj/STATIC_LIBRARIES/libmesa_pipe_svga_intermediates/libmesa_pipe_svga.a)
Traceback (most recent call last):File "external/mesa/src/compiler/glsl/ir_expression_operation.py", line 24, in <module>import mako.template
ImportError: No module named mako.template
make: *** [out/target/product/x86/gen/STATIC_LIBRARIES/libmesa_glsl_intermediates/glsl/ir_expression_operation.h] Error 1
make: *** Deleting file `out/target/product/x86/gen/STATIC_LIBRARIES/libmesa_glsl_intermediates/glsl/ir_expression_operation.h'

解决方案

sudo apt-get install python-mako

问题八描述

xgettext -L C --from-code utf-8 -o out/target/product/x86/gen/STATIC_LIBRARIES/libmesa_dri_common_intermediates/xmlpool.pot external/mesa/src/mesa/drivers/dri/common/xmlpool/t_options.h
/bin/bash: xgettext: command not found
make: *** [out/target/product/x86/gen/STATIC_LIBRARIES/libmesa_dri_common_intermediates/xmlpool.pot] Error 127

解决方数

sudo apt-get install xgettext

问题九描述

external/mesa/src/egl/drivers/dri2/platform_android.c:37:23: fatal error: sync/sync.h: No such file or directory#include <sync/sync.h>^
compilation terminated.

解决方案

vi external/mesa/src/egl/Android.mkLOCAL_C_INCLUDES 下添加 $(MESA_TOP)/../../system/core/libsync/include- $(MESA_TOP)/src/gallium/include
+ $(MESA_TOP)/src/gallium/include \
+ $(MESA_TOP)/../../system/core/libsync/include

问题十描述

/bin/sh: 1: bc: not found
make[3]: *** [include/generated/timeconst.h] Error 127

解决方案

sudo apt-get update
sudo apt-get install bc

问题十一描述

 ERROR: /home/barry/Android-x86/marshmallow-x86/packages/apps/PackageInstaller/src/com/android/packageinstaller/permission/ui/OverlayTouchActivity.java:18: The import android.view.WindowManager.LayoutParams.PRIVATE_FLAG_HIDE_NON_SYSTEM_OVERLAY_WINDOWS cannot be resolved
ERROR: /home/barry/Android-x86/marshmallow-x86/packages/apps/PackageInstaller/src/com/android/packageinstaller/permission/ui/OverlayTouchActivity.java:35: PRIVATE_FLAG_HIDE_NON_SYSTEM_OVERLAY_WINDOWS cannot be resolved to a variable
make: *** [out/target/common/obj/APPS/PackageInstaller_intermediates/with-local/classes.dex] Error 41

解决方案

使用grep搜索了下,源码里的确没有PRIVATE_FLAG_HIDE_NON_SYSTEM_OVERLAY_WINDOWS常量。

执行 `vi packages/apps/PackageInstaller/src/com/android/packageinstaller/permission/ui/OverlayTouchActivity.java`指令,编辑`OverlayTouchActivity.java`文件注释以下代码
package com.android.packageinstaller.permission.ui;-import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_HIDE_NON_SYSTEM_OVERLAY_WINDOWS;
+// import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_HIDE_NON_SYSTEM_OVERLAY_WINDOWS;import android.app.Activity;import android.content.Intent;
@@ -30,11 +30,11 @@ public class OverlayTouchActivity extends Activity {return mObscuredTouch;}-    @Override
-    protected void onCreate(Bundle savedInstanceState) {
-        getWindow().addPrivateFlags(PRIVATE_FLAG_HIDE_NON_SYSTEM_OVERLAY_WINDOWS);
-        super.onCreate(savedInstanceState);
-    }
+    // @Override
+    // protected void onCreate(Bundle savedInstanceState) {
+       // getWindow().addPrivateFlags(PRIVATE_FLAG_HIDE_NON_SYSTEM_OVERLAY_WINDOWS);
+       // super.onCreate(savedInstanceState);
+    // }

问题十二描述

/bin/bash: genisoimage: command not found

解决方案

制作 iso 镜像文件需要的添加的依赖

sudo apt-get install genisoimage

问题十三描述

/bin/bash: isohybrid: command not found
isohybrid not found.
Install syslinux 4.0 or higher if you want to build a usb bootable iso.out/target/product/x86/android_x86.iso is built successfully.用编译好的 iso 镜像文件制作 U 盘启动盘,安装在 x86 主板上不能启动

解决方案

官网介绍编译的 x86 镜像是支持混合 iso 格式,也就是说 iso 可以直接转储到 usb 磁盘上,但是前提需要我们将 iso 镜像转成混合模式的。下面分别介绍在 windows 和 linux 下转化方法:

sudo apt-get install syslinux-utilswindows,使用 rufus 第三方软件
linux, 使用 isohybrid 命令,例如 isohybrid ~/xxx.iso

特别注意,一定要看

其中,问题二、三、四、五都是 Mac 系统不区分大小写造成的,而且即使修复这些问题编译出来的系统也不能正常工作,存在 Bug。因为不区分大小写,许多文件下载的时候都不会写入。 我遇到过编译成功的系统网络不能正常工作,后来我将我的 Mac Pro 分割出一个识别大小的分区,这样编译出来的系统才是正常的。

总结

OK,至此 Android-x8-6.0 源码的编译就大功告成了,接下来我们就可以随心所欲地阅读和修改源码内容,定制 Android 系统了!

Android-x86-6.0定制之路 - 在Ubuntu 16.04.5上编译相关推荐

  1. Anaconda Python3.6 OpenCV4.1.0 Ubuntu 16.04源码编译

    Anaconda Python3.6 OpenCV4.1.0 Ubuntu 16.04源码编译 转载于:https://blog.csdn.net/phdsky/article/details/782 ...

  2. [Android 编译(一)] Ubuntu 16.04 LTS 成功编译 Android 6.0 源码教程

    1 前言 经过3天奋战,终于在Ubuntu 16.04上把Android 6.0的源码编译出来了,各种配置,各种error,各种爬坑,特写此博客记录爬坑经历.先上图,Ubuntu上编译完后成功运行模拟 ...

  3. Ubuntu 16.04系统中编译安装FFmpeg 4.2.1(Android NDK r20)

    1.下载FFmpeg 4.2.1的源码,下载Android NDK r20,安装yasm sudo apt-get install yasm 2.解压缩源码包和Android NDK 3.修改ffmp ...

  4. Ubuntu 16.04源码编译安装nginx 1.10.0

    一.下载相关的依赖库 pcre 下载地址 http://120.52.73.43/jaist.dl.sourceforge.net/project/pcre/pcre/8.38/pcre-8.38.t ...

  5. 在 Ubuntu 16.04 LTS 上安装 Python 3.6.0

    最近 Python 3 发布了新版本 Python 3.6.0,好像又加入了不少黑魔法!- 由于暂时不能使用 apt-get 的方式安装 Python 3.6,所以还是直接编译源码安装吧. 官网上提供 ...

  6. 【已解决】ubuntu 16.04 源码编译opencv4.5.1 报错 “../../lib/libopencv_imgcodecs.so.4.5.0: undefined reference t”

    源码编译opencv可参考教程:在ubuntu下安装opencv4.1.0详细步骤https://blog.csdn.net/weixin_44003563/article/details/90404 ...

  7. ubuntu 16.04配置嵌入式linux开发环境出现Unable to locate package lib32bz2-1.0

    问题描述:Ubuntu16 64位安装android studio的32位库 sudo apt-get install lib32bz2-1.0失败 虚拟机上运行ubuntu 16.04 环境 ,打开 ...

  8. android s905 编译_NanoPi K2 (Amlogic S905) Ubuntu 16.04 编译Android 5.1系统源码

    NanoPi K2 (Amlogic S905) Ubuntu 16.04 编译Android 5.1系统源码 1. 下载源码 在这里下载https://www.mediafire.com/folde ...

  9. [NVIDIA] Ubuntu 16.04 安装 nvidia-384 + cuda-9.0

    租的腾讯云 GPU 主机,因为要安装 nvidia-384 + cuda-9.0,所以选择系统 Ubuntu 16.04. CUDA,NVIDIA Driver 之间的版本对应关系表格 文章目录 安装 ...

最新文章

  1. 小H和游戏(无根树转有根树,思维)难度⭐⭐⭐★
  2. 分布式系统性能监控工具,初探Pinpoint Agent启动源码
  3. 前端开发中的 正则表达式 及常用正则表达式大全
  4. [分享]MOSS的CSS样式说明,一个老外总结的
  5. oracle 安全桌面,Oracle Secure Global Desktop组件远程漏洞(CVE-2012-1685)
  6. Python学习笔记--数据类型
  7. react 按照一级路由 分包加载
  8. 使用CloudForms实现云运营幸福感的3个步骤
  9. python urllib发送post请求_python爬虫 urllib模块发起post请求过程解析
  10. 力扣209-长度最小的子数组(Java,双指针解法)
  11. 使用Cygwin登录Raspberry PI
  12. Android和H5交互-基础篇
  13. Linux与FreeBSD的多网卡绑定增加服务器流量
  14. Recover through incarnations: RMAN-20208
  15. Code blocks调试教程
  16. 关于ES6 Class语法相关总结
  17. 分类与聚类的本质区别
  18. Windows API一日一练(17)DialogBox和DialogBoxParam函数
  19. 菜鸟教程ajax概念原理及使用
  20. Nginx的rewrite(地址重定向)剖析

热门文章

  1. 黑龙江省力推互联网与畜牧产业深度融合 打造大数据中心
  2. 微信撤回软件安卓版_微信拍一拍撤回软件下载
  3. WMI权限问题:Access is denied, please check whether the [domain-username-password] ..
  4. python 运算太慢怎么办_干货|如何入门 Python 爬虫?爬虫原理及过程详解
  5. AWVS安装(Windows)
  6. 【网络】解释Http协议,URL,Http的格式。
  7. 探究添加水印的多种方式
  8. 学计算机每天应该吃什么,上班族长时间看电脑,哪些食物对眼睛好?
  9. 计算机2010基础试题,2010年国硕士研究生入学统一考试计算机基础试题及答案
  10. python dataframe取行_如何获取pandas DataFrame的最后N行?