wiki:jazz/08-11-16

Version 33 (modified by jazz, 16 years ago) (diff)

--

2008-11-16

Event: SC'08

BUGFIX: jfbterm

  • (續 08-11-15@GMT-6)尋找合理懷疑對象:
    root@intrepid:~/jfbterm-0.4.7# grep "KD_GRAPHICS" *
    vterm.c:        ioctl(0, KDSETMODE, KD_GRAPHICS);
    
    root@intrepid:~/jfbterm-0.4.7# grep "KD_TEXT" *
    main.c:        if (mode == KD_TEXT) {
    vterm.c:        ioctl(0, KDSETMODE, KD_TEXT);
    
    root@intrepid:~/jfbterm-0.4.7# grep "cannot mmap" *
    fbcommon.c:             die("cannot mmap(smem)");
    fbcommon.c:             die("cannot mmap(mmio)");
    fbcommon.c:             print_message("cannot mmap(mmio) : %s\n", strerror(errno));
    
  • 啟用 DEBUG 旗標,編譯 jfbterm,使用 gdb 追蹤
    root@intrepid:~/jfbterm-0.4.7# ./configure --enable-debug
    root@intrepid:~/jfbterm-0.4.7# make
    root@intrepid:~/jfbterm-0.4.7# gdb ./jfbterm
    (gdb) run
    
  • 縱使用 gdb 還是無法正常跳回文字模式,因此直接追原始碼。
  • 根據錯誤訊息,應該是錯在 fbcommon.c 的第 572 行,往前追造成錯誤的原因是 566 行的 mmap(),歸屬在 tfbm_open() 函數
    < fbcommon.c >
    
    482 void tfbm_open(TFrameBufferMemory* p)
    
    566         p->mmio = (u_char*)mmap(NULL, p->mlen, PROT_READ|PROT_WRITE,
    567                                 MAP_SHARED, p->fh, p->slen);
    568         if ((long)p->mmio == -1) {
    569 #ifdef JFB_MMIO_CHECK
    570                 die("cannot mmap(mmio)");
    571 #else
    572                 print_message("cannot mmap(mmio) : %s\n", strerror(errno));
    573 #endif
    
    < main.c >
    
    368 int main(int argc, char *argv[])
    431         tfbm_open(&gFramebuffer);
    
  • 安裝 manpages-dev 套件,查 mmap 、 strerror 跟 errno 的 manpage。從 cannot mmap(mmio) : Invalid argument 這個錯誤訊息可以判斷 errno 等於 EINVAL。而 mmap 發生 EINVAL 的情形有三種,最可能的原因是第一個:We don't like addr, length, or offset (e.g., they are too large, or not aligned on a page boundary).
  • 這裡注意到 mmap 的 offset 參數必須是 sysconf 中定義 _SC_PAGE_SIZE 的倍數。(offset must be a multiple of the page size as returned by sysconf(_SC_PAGE_SIZE).)
    root@intrepid:~/jfbterm-0.4.7# apt-get install manpages-dev
    
    root@intrepid:~/jfbterm-0.4.7# man errno
    
           EINVAL          Invalid argument (POSIX.1)
    
    void *mmap(void *addr, size_t length, int prot, int flags, int fd, off_t offset);
    
    offset must be a multiple of the page size as returned by sysconf(_SC_PAGE_SIZE).
    
    ERRORS
           EINVAL We don't like addr, length, or offset (e.g., they are too large, or not aligned on a page boundary).
           EINVAL (since Linux 2.6.12) length was 0.
           EINVAL flags contained neither MAP_PRIVATE or MAP_SHARED, or contained both of these values.
    
  • 使用 gdb 設定中斷點在 fbcomm.c 第 566 行並觀察變數狀態
    root@intrepid:~/jfbterm-0.4.7# gdb
    (gdb) file jfbterm
    Reading symbols from /root/jfbterm-0.4.7/jfbterm...done.
    (gdb) set args -e ls
    (gdb) show args
    Argument list to give program being debugged when it is started is "-e ls".
    (gdb) break fbcommon.c:566
    Breakpoint 1 at 0x4034ba: file fbcommon.c, line 566.
    (gdb) run
    ... 略 ...
    Breakpoint 1, tfbm_open (p=0x6146e0) at fbcommon.c:566
    566             p->mmio = (u_char*)mmap(NULL, p->mlen, PROT_READ|PROT_WRITE,
    (gdb) l
    561             }
    562             p->smem = (char *)p->smem + p->soff;
    563
    564             p->moff = (u_long)(fb_fix.mmio_start) & (~PAGE_MASK);
    565             p->mlen = (fb_fix.mmio_len + p->moff + ~PAGE_MASK) & PAGE_MASK;
    566             p->mmio = (u_char*)mmap(NULL, p->mlen, PROT_READ|PROT_WRITE,
    567                                     MAP_SHARED, p->fh, p->slen);
    568             if ((long)p->mmio == -1) {
    569     #ifdef JFB_MMIO_CHECK
    570                     die("cannot mmap(mmio)");
    (gdb) p fb_fix.mmio_len
    $1 = 0
    (gdb) p p->moff
    $2 = 0
    (gdb) p p->mlen
    $3 = 0
    (gdb) p p->fh
    $4 = 6
    (gdb) p p->slen
    $5 = 1572864
    (gdb) p fb_fix.smem_len
    $6 = 1572864
    

UCIMF - jfbterm patch (中文輸入)

Debian

職場態度

  • 我們要向Google學習做人道理?
    現在的上班族,應該要懂得「放下自我好處」(subordinate),要學會「忘記自己」。 
    對待已知的合作伙伴,要非常的信任;對待未知的其他大眾,也要抱持著讓大家一起來做的開放精神。 
    要懂得與他人合作,人終究是群居的動物,一個健全的心理,一定要認定我們是住在一個需要相互倚靠的社會, 
    就像體內的器官,都要相互倚賴才達到某種平衡,大家快樂各司其工作,一起做得很好。 
    

Web Service

Open Source