miniGUI是一个自由软件项目。其目标是提供一个快速、稳定、跨操作系统的图形用户界面(GUI)支持系统,尤其是基于 Linux/uClinux、eCos 以及其他传统 RTOS(如 VxWorks、ThreadX、uC/OS-II、Nucleus 等)的实时嵌入式操作系统。最近在Hi3535的平台上移植miniGUI3.0,并完成Helloworld的用例测试。这里将移植的过程记录如下。

准备工作

  1. Hi3535SDK和开发板一套,并构建Hi3535的嵌入式开发环境(包括linux编译主机、安装交叉编译工具以及在宿主机上安装NFS调试环境等)。

  2. 从官网下载miniGUI源码以及资源包和示例包。点击打开链接

  3. 熟悉海思Hi3535的Framebuffer模块。包括海思Hi3535提供Framebuffer的标准接口以及Hi3535提供的扩展接口(包括设置colorkey,Alpha等),Hi3535的Framebuffer提供的几种工作模式(None Buffer,One Buffer,Double Buffer等)。此外要仔细研读海思Hi3535的SDK中提供关于Framebufer的指导文档以及参考代码。熟悉Hi3535初始化流程以及Framebuffer的使用流程(包括初始化以及绘制Framebuffer)。

初次编译

解压下载的源代码后,先在源代码的根路径下创建_install目录用于保存编译生成文件。运行以下命令进行配置:

./configure --prefix=[mg_path]/libminigui-3.0.12-linux/_install CC=arm-hisiv100nptl-linux-gcc --host=arm-hisiv100nptl-linux --disable-pcxvfb --disable-screensaver --disable-splash --disable-jpgsupport --enable-videoqvfb=no --enable-rtosxvfb=no --enable-pcxvfb=no

注意:[mg_path]为miniGUI 3.0源代码的存储路径,在具体运行时根据实际保存的源代码路径重新写入。

运行以下命令进行编译:

make
make install

编译成功后可在_install目录下看到编译生成的文件。包括四个文件夹,简要说明如下:

  • etc   文件夹下保存运行配置文件miniGUI.cfg,在实际调试过程中需要修改其内容,详见后续章节描述;
  • include 集成miniGUI库时需要使用到的头文件;
  • lib 包括链接库和运行库;
  • share 暂未使用;

加入Hi3535的framebuffer接口文件

miniGUI中Framebuffer部分的接口主要需要完成两个结构体的初始化,即VideoBootStrap和GAL_VideoDevice。可查到上述两个结构体的定义如下:

typedef struct VideoBootStrap {const char *name;const char *desc;int (*available)(void);GAL_VideoDevice *(*create)(int devindex);
} VideoBootStrap;

结构体成员简要说明如下:

  • name为字符串变量,改字符串用于区分运行的平台,因此尽量保持唯一性。这里使用hi3535作为name。此字符串需要跟运行配置文件MiniGUI.cfg中的名称保持一致。
  • desc 描述,目前没有查到有什么限制,本例使用HI3535 Framebuffer Console。
  • available为需要填充的函数,检查framebuffer是否可用。即尝试打开设备,如果打开成功即验证可用。
  • create为需要填充的函数,函数主要完成GAL_VideoDevice变量的初始化。

GAL_VideoDevice的定义详见src/newgal/sysvideo.h文件。

主要说两点:

  • name仍然保持和VideoBootStrap中定义的一致;
  • hidden 成员变量,主要保存Hi3535在后续Framebuffer中操作需要的信息,可根据需要进行定制。本例中暂定义为:
struct GAL_PrivateVideoData
{Uint32             fd;HIFB_BUFFER_S    stCanvasBuf;Uint32          memLen;
};

其中:

  • fd为open Framebuffer设备后的句柄;
  • stCanvasBuf为framebuffer的画布信息(请参考海思文档);
  • memLen为Framebuffer分配的内存长度;

其他为需要填充的函数。

miniGUI3.0.2中的src/newgal中包含hisi文件夹,目前有实现Hi3510/Hi3560/Hi3560a等芯片的接口。本例中添加Hi3535芯片的接口,将海思hi3535的接口文件命名为:hi3535_fbvideo.c和hi3535_fbvideo.h,完成上述两个结构体变量的初始化。首先可使用空函数完成代码。接下来修改配置文件(包括configure和makefile)来编译新增加的Hi3535的接口文件。

修改configure.in文件,增加编译Hi3535

增加如下代码:

dnl Check HI3535 video driver
CheckHI3535Video()
{AC_ARG_ENABLE(videohi3535,
[  --enable-videohi3535     include Hi3535 Video  NEWGAL engine <default=no>],enable_video_hi3535=$enableval)if test "x$enable_video_hi3535" = "xyes"; thenAC_DEFINE(_MGGAL_HI3535, 1,[Define if include Hi3535 Video NEWGAL engine])VIDEO_SUBDIRS="$VIDEO_SUBDIRS hisi"VIDEO_DRIVERS="$VIDEO_DRIVERS hisi/libvideo_hisifbcon.la"fi
}

增加调用上述代码:

dnl Checks NewGAL Engine.
{CheckDummyVideoCheckFBCONCheckQVFBCheckXVFBCheckWVFBCheckCOMMLCDCheckShadowVideoCheckMLShadowVideoCheckEM85xxOSDCheckEM85xxYUVCheckEM86GFXCheckSvpxxosdVideoCheckBF533VideoCheckMB93493VideoCheckUTPMCVideoCheckDirectFBVideoCheckSTGFBVideoCheckHI35XXVideoCheckHI3560AVideoCheckHI3535VideoCheckGDLVideoCheckNexusVideoCheckS3C6410VideoCheckCustomVideoCheckSigmaVideoCheckMStarVideo
}

修改makefile相关文件

修改src/newgal/hisi目录下的make.in文件

am__objects_1 = hi3510_fbvideo.lo gal_hi3560a.lo hi3560_fbvideo.lo hi3535_fbvideo.lo \pix_array.lo tde.lo

上述属于修改,找到am__objects_1的变量,增加hi3535_fbvideo.lo

SRC_FILES = hi3510_fbvideo.c gal_hi3560a.c hi3560_fbvideo.c hi3535_fbvideo.c pix_array.c tde.c
HDR_FILES = hi3510_fb.h hi3560_fb.h hi3510_fbvideo.h hi3560_fbvideo.h hi3535_fbvideo.h \hi_tde.h tde_reg.h gal_hi3560a.h

上述属于修改,找到SRC_FILES和HDR_FILES变量,分别添加hi3535_fbvideo.c和hi3535_fbvideo.h

@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/hi3535_fbvideo.Plo@am__quote@

上述属于增加的行,参考现有海思芯片的类型进行添加。

修改src/newgal/hisi目录下的makefile.am

SRC_FILES = hi3510_fbvideo.c gal_hi3560a.c hi3560_fbvideo.c hi3535_fbvideo.c pix_array.c tde.c
HDR_FILES = hi3510_fb.h hi3560_fb.h hi3510_fbvideo.h hi3560_fbvideo.h hi3535_fbvideo.h \hi_tde.h tde_reg.h gal_hi3560a.h

完成四个基础函数的填充。

static int HI3535_Available(void)
{const char *GAL_fbdev;int fd;GAL_fbdev = getenv("FRAMEBUFFER");if ( GAL_fbdev == NULL ) {GAL_fbdev = "/dev/fb0";}fd = open(GAL_fbdev, O_RDWR, 0);if ( fd < 0 ) {fprintf(stderr, "failed to open file :%s!\n", GAL_fbdev);return 0;}else{close(fd);return 1;}
}

Hi3535默认加载Framebuffer,因此可以在/dev目录下找到fb0的设备节点文件。上述函数只是尝试打开/dev/fb0文件,如果能够成功打开并获取句柄,则返回成功,否则,返回失败。

static GAL_VideoDevice *HI3535_CreateDevice (int devindex)
{GAL_VideoDevice *this;/* Initialize all variables that we clean on shutdown */this = (GAL_VideoDevice *)malloc(sizeof(GAL_VideoDevice));if ( this ) {memset(this, 0, (sizeof *this));this->hidden = (struct GAL_PrivateVideoData *)malloc(sizeof (struct GAL_PrivateVideoData));this->name = "hi3535";}if ( (this == NULL) || (this->hidden == NULL) ) {GAL_OutOfMemory();if ( this ) {free(this);}return(0);}memset(this->hidden, 0, (sizeof (struct GAL_PrivateVideoData)));/* Set the function pointers */this->VideoInit = HI3535_VideoInit;this->ListModes = HI3535_ListModes;this->SetVideoMode = HI3535_SetVideoMode;this->ToggleFullScreen = HI3535_ToggleFullScreen;this->SetColors = HI3535_SetColors;this->UpdateRects = HI3535_UpdateRects;this->VideoQuit = HI3535_VideoQuit;
#ifndef _MGRM_THREADSthis->RequestHWSurface = HI3535_RequestHWSurface;
#endifthis->AllocHWSurface = HI3535_AllocHWSurface;this->CheckHWBlit = HI3535_CheckHWBlit;this->FillHWRect = HI3535_FillHWRect;this->SetHWColorKey = HI3535_SetHWColorKey;this->SetHWAlpha = HI3535_SetHWAlpha;this->FreeHWSurface = HI3535_FreeHWSurface;this->free = HI3535_FBFree;this->DeleteSurface = HI3535_DeleteSurface;this->SetSurfaceColors = HI3535_SetSurfaceColors;this->GetFBInfo = HI3535_GetFBInfo;this->UpdateSurfaceRects = HI3535_UpdateSurfaceRects;return this;
}

上述函数主要用于创建GAL_VideoDevice结构体变量,初始化并返回。并且分配hidden成员变量的空间。

extern int hi3535_board_init(void);

外部初始化函数,用于实现初始化Hi3535平台。可参考海思SDK中的sample示例。因为miniGUI运行时,并不会去完成平台初始化的工作,因此在miniGUI调用其库完成framebuffer的接口初始化之前,要借助此外部函数完成平台初始化,以确保framebuffer的初始化及相关操作不会出错。

static int HI3535_VideoInit(GAL_VideoDevice *this, GAL_PixelFormat *vformat)
{struct fb_fix_screeninfo finfo;struct fb_var_screeninfo vinfo;int i;const char *GAL_fbdev;GAL_VideoInfo* paccel_info =  &this->info;HIFB_COLORKEY_S            stColorKey;HIFB_POINT_S             stPoint;HIFB_LAYER_INFO_S       stLayerInfo = {0};HI_BOOL                  bShow; hi3535_board_init();/* 1. open Framebuffer device overlay 0 */GAL_fbdev = getenv("FRAMEBUFFER");if ( GAL_fbdev == NULL ) {GAL_fbdev = "/dev/fb0";}this->hidden->fd = open(GAL_fbdev, O_RDWR, 0);if ( this->hidden->fd < 0 ) {GAL_SetError("NEWGAL>HI3535: Unable to open %s\n", GAL_fbdev);return -1;}/*2. all layer surport colorkey*/ stColorKey.bKeyEnable   = HI_TRUE;stColorKey.u32Key        = 0x0;if (ioctl(this->hidden->fd, FBIOPUT_COLORKEY_HIFB, &stColorKey) < 0){GAL_SetError("NEWGAL>HI3535:FBIOPUT_COLORKEY_HIFB!\n");return -2;}/* 3. set the screen original position */stPoint.s32XPos = 0;stPoint.s32YPos = 0;if (ioctl(this->hidden->fd, FBIOPUT_SCREEN_ORIGIN_HIFB, &stPoint) < 0){GAL_SetError("NEWGAL>HI3535:set screen original show position failed!\n");return -3;}/* 4. get the variable screen info */if(ioctl(this->hidden->fd, FBIOGET_VSCREENINFO, &vinfo) < 0){GAL_SetError("NEWGAL>HI3535:GET_VSCREENINFO failed!\n");return -4;} /* 5. config the default parameters of the variable screen. */vinfo.xres_virtual       = DEFAULT_SCREEN_WIDTH;vinfo.yres_virtual      = DEFAULT_SCREEN_HEIGHT;vinfo.xres             = DEFAULT_SCREEN_WIDTH;vinfo.yres          = DEFAULT_SCREEN_HEIGHT;vinfo.transp           = s_a16;vinfo.red              = s_r16;vinfo.green            = s_g16;vinfo.blue             = s_b16;vinfo.bits_per_pixel   = 16;vinfo.activate            = FB_ACTIVATE_NOW;if (ioctl(this->hidden->fd, FBIOPUT_VSCREENINFO, &vinfo) < 0){GAL_SetError("NEWGAL>HI3535: Put variable screen info failed!\n");return -5;}/* 6. set one buffer mode. */stLayerInfo.BufMode    = HIFB_LAYER_BUF_ONE;stLayerInfo.u32Mask   = HIFB_LAYERMASK_BUFMODE;if(ioctl(this->hidden->fd, FBIOPUT_LAYER_INFO, &stLayerInfo) < 0){GAL_SetError("NEWGAL>HI3535: PUT_LAYER_INFO failed!\n");return -6;}bShow = HI_TRUE;if (ioctl(this->hidden->fd, FBIOPUT_SHOW_HIFB, &bShow) < 0){GAL_SetError("NEWGAL>HI3535:FBIOPUT_SHOW_HIFB failed!\n");return -7;}/* 7. Get the type of video hardware */if ( ioctl(this->hidden->fd, FBIOGET_FSCREENINFO, &finfo) < 0 ) {GAL_SetError("NEWGAL>HI3535: Couldn't get console hardware info\n");HI3535_VideoQuit(this);return -6;}/* Memory map the device, compensating for buggy PPC mmap() */this->hidden->stCanvasBuf.stCanvas.u32PhyAddr = mmap(NULL, finfo.smem_len,PROT_READ|PROT_WRITE, MAP_SHARED, this->hidden->fd, 0);this->hidden->stCanvasBuf.stCanvas.u32Width = vinfo.xres;this->hidden->stCanvasBuf.stCanvas.u32Height = vinfo.yres;this->hidden->stCanvasBuf.stCanvas.u32Pitch = vinfo.xres*2;this->hidden->stCanvasBuf.stCanvas.enFmt = HIFB_FMT_ARGB1555;memset((Uint16*)(this->hidden->stCanvasBuf.stCanvas.u32PhyAddr), 0x00, this->hidden->stCanvasBuf.stCanvas.u32Pitch*this->hidden->stCanvasBuf.stCanvas.u32Height);this->hidden->memLen = finfo.smem_len;vformat->BitsPerPixel = vinfo.bits_per_pixel;for ( i=0; i<vinfo.red.length; ++i ) {vformat->Rmask <<= 1;vformat->Rmask |= (0x00000001<<vinfo.red.offset);}for ( i=0; i<vinfo.green.length; ++i ) {vformat->Gmask <<= 1;vformat->Gmask |= (0x00000001<<vinfo.green.offset);}for ( i=0; i<vinfo.blue.length; ++i ) {vformat->Bmask <<= 1;vformat->Bmask |= (0x00000001<<vinfo.blue.offset);}for ( i=0; i<vinfo.transp.length; ++i ) {vformat->Amask <<= 1;vformat->Amask |= (0x00000001<<vinfo.transp.offset);}paccel_info->hw_available = 1;paccel_info->video_mem = finfo.smem_len/1024;paccel_info->blit_fill = 1;paccel_info->blit_hw = 1;paccel_info->blit_hw_A = 1;paccel_info->blit_hw_CC = 1;return(0);
}

参考sample_hifb.c中的初始化过程实现。但在内存映射上做了修改。

static GAL_Surface *HI3535_SetVideoMode(GAL_VideoDevice *this, GAL_Surface *current, int width, int height, int bpp, Uint32 flags)
{struct fb_fix_screeninfo finfo;struct fb_var_screeninfo vinfo;int i;Uint32 Rmask;Uint32 Gmask;Uint32 Bmask;Uint32 Amask;char *surfaces_mem;int surfaces_len;/* Set the video mode and get the final screen format */if ( ioctl(this->hidden->fd, FBIOGET_VSCREENINFO, &vinfo) < 0 ) {fprintf (stderr, "Couldn't get console screen info");return(NULL);}if ((vinfo.xres != width) || (vinfo.yres != height) ||(vinfo.bits_per_pixel != bpp)){vinfo.activate = FB_ACTIVATE_NOW;vinfo.accel_flags = 0;vinfo.bits_per_pixel = bpp;vinfo.xres = width;vinfo.xres_virtual = width;vinfo.yres = height;vinfo.yres_virtual = height;vinfo.xoffset = 0;vinfo.yoffset = 0;vinfo.red.length = vinfo.red.offset = 0;vinfo.green.length = vinfo.green.offset = 0;vinfo.blue.length = vinfo.blue.offset = 0;vinfo.transp.length = vinfo.transp.offset = 0;if ( ioctl(this->hidden->fd, FBIOPUT_VSCREENINFO, &vinfo) < 0 ) {GAL_SetError("NEWGAL>HI3535: Couldn't set console screen info\n");vinfo.yres_virtual = height;if ( ioctl(this->hidden->fd, FBIOPUT_VSCREENINFO, &vinfo) < 0 ) {GAL_SetError("NEWGAL>HI3535: Couldn't set console screen info[2]\n");return(NULL);}}}else{int maxheight;/* Figure out how much video memory is available */maxheight = height;if ( vinfo.yres_virtual > maxheight ) {vinfo.yres_virtual = maxheight;}}Rmask = 0;for ( i=0; i<vinfo.red.length; ++i ) {Rmask <<= 1;Rmask |= (0x00000001<<vinfo.red.offset);}Gmask = 0;for ( i=0; i<vinfo.green.length; ++i ) {Gmask <<= 1;Gmask |= (0x00000001<<vinfo.green.offset);}Bmask = 0;for ( i=0; i<vinfo.blue.length; ++i ) {Bmask <<= 1;Bmask |= (0x00000001<<vinfo.blue.offset);}Amask = 0;for ( i=0; i<vinfo.transp.length; ++i ) {Amask <<= 1;Amask |= (0x00000001<<vinfo.transp.offset);}if (!GAL_ReallocFormat(current, vinfo.bits_per_pixel,Rmask, Gmask, Bmask, Amask) ) {return(NULL);}if ( vinfo.bits_per_pixel < 8 ) {current->format->MSBLeft = !(vinfo.red.msb_right);}/* Set up the new mode framebuffer */current->flags = GAL_FULLSCREEN;current->w = vinfo.xres;current->h = vinfo.yres;current->pitch = vinfo.xres*2;current->pixels = this->hidden->stCanvasBuf.stCanvas.u32PhyAddr;return(current);
}

最后在hi3535_fbvideo.c中包含hi3535SDK中与Framebuffer有关的头文件:hi_type.h和hifb.h,并将这两个头文件拷贝到src/newgal/hisi目录下。

完成后重新配置编译,在配置之前先运行make distclean清除之前的配置

./configure --prefix=/home/zkliu/miniGUI/libminigui-3.0.12-linux/_install CC=arm-hisiv100nptl-linux-gcc --host=arm-hisiv100nptl-linux --disable-pcxvfb --disable-screensaver --disable-splash --disable-jpgsupport --enable-videoqvfb=no --enable-rtosxvfb=no --enable-pcxvfb=no --enable-videohi3535=yes

注意增加了对hi3535的支持

然后编译全套代码:

make
make install

测试

准备资源文件

解压miniGUI的资源文件,在资源文件根目录下建立_install目录。运行一下命令配置编译:

./configure --host=arm-hisiv100nptl-linux  --prefix=[mg_res]/ minigui-res-be-3.0.12 /_install
make
make install

成功编译完成后在_install目录下可得到需要的资源文件。

建立helloworld sample

在hi3535SDK中的sample目录下建立一个单独的目录,比如miniGUI。拷贝helloworld.c(该文件来自于miniGUI网站中的sample实例)文件到目录下。拷贝_install下的include目录到miniGUI目录下。拷贝_install/lib/ libminigui_ths.a文件到miniGUI/lib目录下。新建board.c文件,实现int hi3535_board_init(void);包括sys模块、VO、HDMI等跟输出相关模块的初始化。修改miniGUI目录下的makefile如下:

# Hisilicon Hi3535 sample Makefileinclude ../Makefile.param# target source
SRC  := $(wildcard *.c)
OBJ  := $(SRC:%.c=%.o)TARGET := helloworld
.PHONY : clean allall: $(TARGET)MPI_LIBS := $(REL_LIB)/libmpi.a
MPI_LIBS += $(REL_LIB)/libhdmi.a
CFLAGS += -I./include $(TARGET):$(OBJ)$(CC) $(CFLAGS) -lpthread -lm -o $@ $^ $(MPI_LIBS) $(AUDIO_LIBA) -L./lib -lminigui_ths%.o:%.c$(CC) -c $(CFLAGS) $^ -o $@clean:@rm -f $(TARGET)@rm -f $(OBJ)

在sample文件夹下的makefile中增加对miniGUI文件夹的编译:

mg:@cd miniGUI; makemg_clean:@cd miniGUI; make clean

至此,可对helloworld例子进行编译。

建立调试目录

将资源文件_install/share/minigui目录拷贝的nfs挂载目录,将miniGUI动态库和软连接文件拷贝到nfs挂载目录中的miniGUILibs目录(如果没有就新建)。软连接文件如果失效,使用ln –sf命令重新建立软连接。拷贝示例helloworld到nfs挂载目录。修改miniGUI.cfg文件如下:

[system]
# GAL engine and default options
gal_engine=hi3535
defaultmode=800x600-16bpp# IAL engine
ial_engine=dummy
mdev=/dev/input/mice
mtype=IMPS2[fbcon]
defaultmode=1024x768-16bpp[hi3535]
defaultmode=1920x1080-16bpp

第3行修改gal_engine:

第14行增加hi3535 gal_engine定义,设置缺省分辨率。

修改鼠标资源文件定向,找到以下位置修改:

cursorpath=./minigui/res/cursor/

修改图片资源文件定向,找到以下位置修改:

respath=./minigui/res/

完成上述修改后将miniGUI.cfg拷贝到nfs挂载目录下。

修改Hi3535单板上/etc/profile文件,将miniGUI的动态库文件所在路径包含到LD_LIBRARY_PATH变量中:

LD_LIBRARY_PATH="/usr/local/lib:/usr/lib:/mnt/miniGUILibs"

运行示例:./helloworld

可在HDMI接口看到欢迎窗口如图:

参考文献

  1. Minigui3在海思Hi3520D/Hi3531平台上运行  https://blog.csdn.net/jhting/article/details/51059484
  2. HiFBAPI参考.pdf
  3. HiFB开发指南.pdf

源代码资源已上传,下载地址点击打开链接。

miniGUI 3.0.2 在Hi3535平台上的移植相关推荐

  1. Ubuntu-Base 18 文件系统 在iMX8平台上的移植

    Ubuntu-Base 18 文件系统 在iMX8平台上的移植 开发板是如下的型号 OKMX8MPX-C V2.0 OKMX8PQ-C开发板 FETMX8MPX-C V1.0 在 飞凌 提供的 ubu ...

  2. opus在arm的嵌入式平台上的移植和开发

    最近产品中要用到opus,圣上一声令下,把opus移植到我们平台上,什么?opus?opus是什么?在一脸 茫然中,我这特种兵码农就赤手空拳上战场了. 废话少说,赶紧在网站:https://opus- ...

  3. ARMBoot-1.1.0 在 mini2440 开发板上的移植 之稻草人手记

    ARMBoot-1.1.0 在 mini2440 开发板上的移植 之稻草人手记 < snallieATtomDOTcom > 作为U-boot的鼻祖-ARMboot以其小巧玲珑(代码压缩包 ...

  4. QT4.7.3在dm6446平台上的移植[转]--make[1]: *** [assistant_cs.qm] Error 2

    师兄让我作达芬奇系统下的一个界面程序,听说QT不错,所以几天前就试着把QT移植到dm6446上来.去TI的论坛看了一个在omap3上的移植教程,看起来也不难,于是开始了我的移植过程. 1 首先去htt ...

  5. 锐捷认证客户端在嵌入式linux平台上的移植

    一.TCP/IP协议简介 IP协议用于将多个包交换网络连接起来,IP不提供可靠的传输服务,它不提供端到端的或(路由)结点到(路由)结点的确认,对数据没有差错控制,它只使用报头的校验码,它不提供重发和流 ...

  6. Ubuntu-Base在iMX8MM平台上的移植

    先说废话↓ 转眼大学快过完了,已经开始了毕业设计的开发.笔者的毕业设计是一个运行ARM-Linux的第一人称控制机器人,为了挑(zhe)战(mo)一下自己,选择了一个性能很美丽的平台--iMX8MM, ...

  7. Qt4.7.3在dm6446平台上的移植经验与教训

    1 首先去http://qt.nokia.com/downloads下载最新的QT原代码包:qt-everywhere-opensource-src-4.6.4.tar.gz 可以将其放在/tmp目录 ...

  8. 创维 linux内核,Linux2.6内核在创维特jx2410平台上的移植一

    我参考网上的资料做了linux2.6.14内核的移植.创维特jx2410的配置:cpu:s3c2410, 32M Nor Flash(Intel 28F128), 64M SDRAM.Nor Flas ...

  9. FFTW3在android平台上的移植

    目的:编译arm64-v8a armeabi-v7a架构的动态库 编译环境:ubuntu 64 + android-ndk-r10e 注意事项:一定要保证android-ndk-r10e的有足够的权限 ...

最新文章

  1. 提高php编程效率的小结
  2. 李飞飞最新论文:用算法判断政治倾向(附论文链接)
  3. 大脑如何编码视觉信息?动态电极到图像(DETI) 映射技术也许有助于我们揭示其原理...
  4. 复制(主从复制、读写分离)
  5. python打包的exe开机自动启动(windows)
  6. GPU Gems1 - 5 改良的Perlin噪声的实现
  7. 团队冲刺第一阶段第三天
  8. spring boot—默认日志框架配置
  9. 程序员伪装 AI 编程,竟骗来 2 亿的投资!
  10. 用Aspose.Words 从Word文档中提取表格数据
  11. 每天10个Linux命令五
  12. ubuntu 怎么下载android源代码 2013,简记Ubuntu下载 Android源码(示例代码)
  13. hydra 破解ssh 163邮箱
  14. 网易互娱游戏研发工程师笔试
  15. Android 安卓动画 补间动画 - 缩放动画
  16. 如何用计算机学唱歌,男孩学唱歌教程 男生如何练习唱歌?
  17. function Function函数
  18. VIM中ctags的简单使用教程
  19. 【坤坤讲师--图】Dinic
  20. 全球语言标准码及其国家或地区对照

热门文章

  1. 二极管的最高工作频率的决定因素是什么?
  2. 一个优秀的RPC框架需要考虑的问题
  3. MCS-51 单片机的结构和工作原理
  4. 精彩书摘:团队建立初期要做的事情
  5. webpack版本升级的差异大版本更迭
  6. 一个简单的电子邮箱验证
  7. 计算机巨人的采访对话英文怎么说,采访明星的英文对话稿。
  8. 结构-行为-样式-angularJs 指令实现滚动文字
  9. 学校员工管理系统流程图以及项目源码(c++超详细)
  10. 深度学习笔记------注意力机制