VIM에서 컬럼 너비 체크 및 수정

Posted at 2012/08/22 18:45 // in Programming // by Daniel
코드 짤 때 컬럼 너비가 80으로 정해져있는데 내 코드에 가끔 그보다 넓게 짜서 수정해야 할 때,
vim에서는 gqq 라는 명령어가 있습니다.
gqq를 누르면 해당 라인이 설정된 컬럼 너비에 맞게 변화됩니다.
http://stackoverflow.com/questions/3033 ··· -columns
컬럼 너비 설정은
set textwidth=80 으로 합니다.

그리고 컬럼 너비가 너무 긴 행을 표시하려면 .vimrc에 다음과 같이 추가하면 됩니다.
highlight OverLength ctermbg=red ctermfg=white guibg=#592929
match OverLength /\%81v.\+/

이렇게 해놓으면 80 컬럼을 넘는 긴 행이 빨간 색으로 표시됩니다.
http://stackoverflow.com/questions/2354 ··· concerns

크리에이티브 커먼즈 라이센스
Creative Commons License

간단한 큐

Posted at 2012/03/23 17:25 // by Daniel

보호되어 있는 글 입니다.
내용을 보시려면 비밀번호를 입력하세요.

Nokia QT 개발환경 세팅중

Posted at 2010/06/12 08:05 // in Programming // by Daniel

http://developer.symbian.org/wiki/index ··· ck_start

image

노키아가 QT를 조만간 기본 환경으로 쓸 거라고 해서

(자바로 할까 했으나)

일단 이걸로 개발해보기로 했습니다. (..하지만 시간이 있을 지 과연..)

 

http://www.forum.nokia.com/info/sw.noki ··· sdk.html

image

image

크리에이티브 커먼즈 라이센스
Creative Commons License

No silver Bullet

Posted at 2010/04/22 10:14 // in Programming // by Daniel
The Mythical Man-month에 나온 이야기
유명한 페이퍼입니다.

소프트웨어 개발에 하나의 방법으로 모든 도메인에 일정과 품질을 향상시키는 "마법의 탄환"은 없다는거죠 :-)
pdf 출처는 http://people.eecs.ku.edu/~saiedian/Teaching/Sp08/816/Papers/Background-Papers/no-silver-bullet.pdf 입니다. 구글검색 :-)

크리에이티브 커먼즈 라이센스
Creative Commons License

간단한 FIFO queue 예제

Posted at 2010/04/22 08:35 // in Programming // by Daniel

#include <stdio.h>

static char qout( void );
static int qin( char in );
static int  qlen ( void );
#define Q_MAX   4
int queue[Q_MAX];
int qhead=0;
int qtail=0;
int main(void)
{
    char io;
    char input;
    int exit=0;
    int state=0;
    char rd;
    printf("simple queue test\n");
    fflush(stdin);
    do {
        switch(state) {
            case 0:
                printf("cmd $ ");
                state = 1;
            case 1:
                fflush(stdout);
                fflush(stdin);
                rd = getchar();
                if (rd==' ' || rd=='\n')
                    continue;
                if (rd=='q') {
                    exit=1;
                    break;
                }
                // get cmd;
                if (rd=='i')
                    state = 5;
                if (rd=='o')
                    state = 10;
                break;
            case 5:
                // input
                printf("input$ ");
                state = 6;
            case 6:
                fflush(stdout);
                fflush(stdin);
                rd = getchar();
                if (rd==' ' || rd=='\n')
                    continue;
                if (rd=='q') {
                    exit=1;
                    break;
                }
                input = rd;
                qin(input);
                printf("h=%d, tail=%d qlen=%d\n", qhead, qtail, qlen());
                state = 0;
                break;
            case 10:
                // get

                printf("%c\n", qout());
                printf("h=%d, tail=%d qlen=%d\n", qhead, qtail, qlen());
                state = 0;
                break;
            default:
                printf("default state??\n");
                exit=1;
        } // switch
    } while(!exit);

    return 0;
}

static int  qlen ( void )
{
    if ( qhead >= qtail )
        return qhead-qtail;
    return qhead+Q_MAX+1-qtail;
}

static int qin( char in )
{
    int tmp_head = qhead;
    tmp_head++;
    if (tmp_head==(Q_MAX+1))
        tmp_head=0;
    if (tmp_head==qtail) {
        // overrun
        fprintf(stderr, "q overrun\n");
        return -1;
    }
    printf("q[%d]<:=%c\n", qhead, in);
    queue[qhead] = in;
    qhead = tmp_head;
    return 0;
}

static char qout( void )
{
    int tmp_tail = qtail;
    if (qtail == qhead) {
        // underrun
        fprintf(stderr, "q underrun\n");
        return '\b';
    }
    qtail = (tmp_tail +1 );
    if (qtail == (Q_MAX+1))
        qtail = 0;
    printf("q[%d]==%c\n", tmp_tail, queue[tmp_tail]);
    return queue[tmp_tail];
}

리팩토링 필요 – 리팩토링 했지만 여기에 게시하진 않음.
크리에이티브 커먼즈 라이센스
Creative Commons License

(C프로그램) 매크로 정의시 안전한 방법

Posted at 2010/04/20 10:31 // in Programming // by Daniel

do { ... } while(0)로 묶기

http://kernelnewbies.org/FAQ/DoWhile0, http://kldp.org/node/41390, http://blog.dasomoli.org/220

안전한 방법은 do{}while(0)로 묶는 것입니다.

#define foo(x) do{ printf(“it’s %d\n”, x); \
                 do_something(x);\
               } while (0)

일반적으로 C에서 매크로를 짜면

#define FOO(x) \
        printf("arg is %s\n", x); \
        do_something_useful(x);

이런 식으로 짜게 됩니다.

그러나 이런 방식은 맹점이 있습니다.

예를 들어

        if (blah == 2)
                FOO(blah);

이렇게 쓰면

        if (blah == 2)
                printf("arg is %s\n", blah);
                do_something_useful(blah);;

이렇게 해석돼 버립니다.

만일 do{ … }while(0)로 만들었다면

if (blah == 2)
        do {
                printf("arg is %s\n", blah);
                do_something_useful(blah);
        } while (0);

이렇게 원하는 대로 해석됩니다.

그렇다고

        #define exch(x,y) { int tmp; tmp=x; x=y; y=tmp; }

이렇게 쓰면

if (x > y)
        exch(x,y);          // Branch 1
else 
        do_something();     // Branch 2

이런 문장이

if (x > y) {                // Single-branch if-statement!!!
        int tmp;            // The one and only branch consists
        tmp = x;            // of the block.
        x = y;
        y = tmp;
}
;                           // empty statement
else                        // ERROR!!! "parse error before else"
        do_something();
이렇게 해석돼 버립니다. –> 컴파일러 에러 발생.
그러므로 do {} while(0)로 묶는 게 최고죠. 그래서 리눅스 커널에서 모든 매크로가 그렇게 돼 있는 겁니다.

매크로에서 쓰는 변수에는 괄호를 꼭 쳐주세요

그리고 한가지 더
매크로에서 쓰는 변수에는 괄호를 꼭 쳐주세요 http://www.oualline.com/style/c06.html

/* Square a number */
#define SQUARE(X) (x * x)
/* Bad practice, no () around parameter */

이렇게 정의하면
a = SQUARE(1 + 3);
-->:
a = (1 + 3 * 1 + 3);
이렇게 돼 버려서 원치 않는 결과가 나옵니다.
/* Square a number */
#define SQUARE(X) ((x) * (x))
이러면
a = ((l + 3) * (1 + 3));
이렇게 잘 나오겠지요.
크리에이티브 커먼즈 라이센스
Creative Commons License

Linux man page들

Posted at 2010/04/18 00:03 // in Programming // by Daniel
cygwin에선 glibc library man page가 없다.
왜냐면 당연히 cygwin이 linux가 아니므로;; (참고)

ubuntu 소스에서 man page를 가져와서 압축했다.
1.3메가.. posix 맨페이지도, 한글맨페이지도 받아다 압축했다.
 man-pages-3.23
man.tgz

Man pages. 1.3MB

man-ko.tgz

한글 man 페이지. 660KB

man-posix.tgz

POSIX man page - 이게 가장 필요할 듯. POSIX 표준관련 man page다. 1.3메가

cygwin에서 설치및 사용법
자기 홈디렉토리 아래
man 디렉토리를 만들고 그 아래에 man1~man8  디렉토리가 들어가도록 한다.
posix도 마찬가지로 man0p man1p man3p 디렉토리가 man 디렉토리 아래에 가도록 한다.
사용자 삽입 이미지

그리고,
~/.bash_profile에서
다음 구절을 추가하거나 주석 해제한다. 결국 당연히 man path를 추가하는 것임. (참고로 한글 man 페이지는 깔기를 추천하지 않음. 깨져나옴.)
# Set MANPATH so it includes users' private man if it exists
if [ -d "${HOME}/man" ]; then
  MANPATH=${HOME}/man:${MANPATH}
fi
# 한글 man페이지는 ~/man/ko에 깔면 되긴 되는데.. 추천하지 않음. 한글 깨집니다.
if [ -d "${HOME}/man/ko" ]; then
  MANPATH=${HOME}/man/ko:${MANPATH}
fi
사용자 삽입 이미지


크리에이티브 커먼즈 라이센스
Creative Commons License

Eddy DK 보드에 1ms 타이머 쓰기

Posted at 2010/03/17 23:19 // in Programming // by Daniel

지금 보드가 없으므로 검색 이후  말로만 하는 거임(틀릴 수 있음)

Eddy DK 보드는 CPU가 Atmel의 AT91SAM9260임

이 칩은 TC타이머가 6개 있음

그런데 Eddy DK의 OS인 레모닉스-리눅스를 조금 고친 것 같은데 소스를 일부만 줌-에서는 타이머 관련 코드가 살아있지 않음 (메모리 영역도 안잡혀있음. 소스를 안준 부분이 있어서 커널 컴파일도 다시 못함)

그래서 직접 하드웨어에 억세스하도록 하고 타이머 돌려보려고 했으나 실패(인터럽트는 커녕 타이머 자체가 돌지 않음)

결국 외부 GPIO에 붙여서 인터럽트 걸어서 사용

 

인터넷을 검색해본 결과 두 가지를 알 수 있었음

1. hrtimer를 쓰면 된다고 하는 사람이 있음

hrtimer는 config에 있는 것을 보았다 – 그런데 nanosleep같은 애들에서 쓴다던데 제대로 안됐다고 하는 거 같음

 

2. tclib이란 게 atmel에서 서포트한 코드가 커널에 있음

http://www.avrfreaks.net/index.php?name=PNphpBB2&file=viewtopic&t=67424

include/linux/atmel_tc.h and drivers/misc/atmel_tclib.c

drivers/clocksource/tcb_clksrc.c can be used as an example of how to use

tclib.

근데 레모닉스에는 일단 tclib이 enable안돼있음(config) 어찌됐든 코드를 붙여넣거나 해서 써야 함

 

 

참고

http://www.mail-archive.com/linux-kerne ··· 782.html
[patch 2.6.25-rc2-git 1/2] atmel_tc library

tclib이라고 원래 atmel 칩 용으로 타이머 라이브러리가 있음..

http://www.spinics.net/lists/arm-kernel/msg58764.html
Arg! Why is it always the case that I find the answer just after I submit the question ... I needed to SYNC the Timer Block. See below for correction.

> __raw_writel(1000, tcaddr + ATMEL_TC_REG(REG_OFFSET, RC));
> __raw_writel(0x0000, tcaddr + ATMEL_TC_REG(REG_OFFSET, RA));
> __raw_writel(0x0000, tcaddr + ATMEL_TC_REG(REG_OFFSET, RB));
> __raw_writel(0xff, tcaddr + ATMEL_TC_REG(REG_OFFSET, IDR));  /* no irqs */
> __raw_writel(ATMEL_TC_CLKEN, tcaddr + ATMEL_TC_REG(REG_OFFSET, CCR));
>
>  
__raw_writel(ATMEL_TC_SYNC, tcaddr + ATMEL_TC_BCR);
> at91_set_B_periph(AT91_PIN_PA19, 0);    /* TIOA1 */
>
> clocksource_register(&clksrc);
>
> ----- UNSNIP ----
>  
My device driver is probably deprecated by the new generic PWM lib from Bill, but I have to release with what I've got.

Aras

크리에이티브 커먼즈 라이센스
Creative Commons License

소프트웨어 크리에이티비티 2.0

Posted at 2009/05/25 14:47 // in Programming // by Daniel

http://jhrogue.blogspot.com/2009/05/20.html

소개받은책.

살까나

크리에이티브 커먼즈 라이센스
Creative Commons License

AT&T Assembly Syntax

Posted at 2009/05/04 11:33 // in Programming // by Daniel

http://sig9.com/articles/att-syntax

http://sourceware.org/binutils/docs-2.16/as/index.html

Updated: May/10 '06

This article is a 'quick-n-dirty' introduction to the AT&T assembly language syntax, as implemented in the GNU Assembler as(1). For the first timer the AT&T syntax may seem a bit confusing, but if you have any kind of assembly language programming background, it's easy to catch up once you have a few rules in mind. I assume you have some familiarity to what is commonly referred to as the INTEL-syntax for assembly language instructions, as described in the x86 manuals. Due to its simplicity, I use the NASM (Netwide Assembler) variant of the INTEL-syntax to cite differences between the formats.

The GNU assembler is a part of the GNU Binary Utilities (binutils), and a back-end to the GNU Compiler Collection. Although as is not the preferred assembler for writing reasonably big assembler programs, its a vital part of contemporary Unix-like systems, especially for kernel-level hacking. Often criticised for its cryptic AT&T-style syntax, it is argued that as was written with an emphasis on being used as a back-end to GCC, with little concern for "developer-friendliness". If you are an assembler programmer hailing from an INTEL-Syntax background, you'll experience a degree of stifling with regard to code-readability and code-generation. Nevertheless, it must be stated that, many operating systems' code-base depend on as as the assembler for generating low-level code.

The Basic Format

The structure of a program in AT&T-syntax is similar to any other assembler-syntax, consisting of a series of directives, labels, instructions - composed of a mnemonic followed by a maximum of three operands. The most prominent difference in the AT&T-syntax stems from the ordering of the operands.

For example, the general format of a basic data movement instruction in INTEL-syntax is,

mnemonic	destination, source

whereas, in the case of AT&T, the general format is

mnemonic	source, destination

To some (including myself), this format is more intuitive. The following sections describe the types of operands to AT&T assembler instructions for the x86 architecture.

Registers

All register names of the IA-32 architecture must be prefixed by a '%' sign, eg. %al,%bx, %ds, %cr0 etc.

mov	%ax, %bx

The above example is the mov instruction that moves the value from the 16-bit register AX to 16-bit register BX.

Literal Values

All literal values must be prefixed by a '$' sign. For example,

 		
mov	$100,	%bx
mov	$A,	%al

The first instruction moves the the value 100 into the register AX and the second one moves the numerical value of the ascii A into the AL register. To make things clearer, note that the below example is not a valid instruction,

mov	%bx,	$100

as it just tries to move the value in register bx to a literal value. It just doesn't make any sense.

Memory Addressing

In the AT&T Syntax, memory is referenced in the following way,

segment-override:signed-offset(base,index,scale)

parts of which can be omitted depending on the address you want.

%es:100(%eax,%ebx,2)

Please note that the offsets and the scale should not be prefixed by '$'. A few more examples with their equivalent NASM-syntax, should make things clearer,

GAS memory operand			NASM memory operand
------------------			-------------------

100					[100]
%es:100					[es:100]
(%eax)					[eax]
(%eax,%ebx)				[eax+ebx]
(%ecx,%ebx,2)				[ecx+ebx*2]
(,%ebx,2)				[ebx*2]
-10(%eax)				[eax-10]
%ds:-10(%ebp)				[ds:ebp-10]
Example instructions,
mov	%ax,	100
mov	%eax,	-100(%eax)

The first instruction moves the value in register AX into offset 100 of the data segment register (by default), and the second one moves the value in eax register to [eax-100].

Operand Sizes

At times, especially when moving literal values to memory, it becomes neccessary to specify the size-of-transfer or the operand-size. For example the instruction,

mov	$10,	100

only specfies that the value 10 is to be moved to the memory offset 100, but not the transfer size. In NASM this is done by adding the casting keyword byte/word/dword etc. to any of the operands. In AT&T syntax, this is done by adding a suffix - b/w/l - to the instruction. For example,

movb	$10,	%es:(%eax)

moves a byte value 10 to the memory location [ea:eax], whereas,

movl	$10,	%es:(%eax)

moves a long value (dword) 10 to the same place.

A few more examples,

movl	$100, %ebx
pushl	%eax
popw	%ax
Control Transfer Instructions

The jmp, call, ret, etc., instructions transfer the control from one part of a program to another. They can be classified as control transfers to the same code segment (near) or to different code segments (far). The possible types of branch addressing are - relative offset (label), register, memory operand, and segment-offset pointers.

Relative offsets, are specified using labels, as shown below.

label1:
	.
	.
  jmp	label1

Branch addressing using registers or memory operands must be prefixed by a '*'. To specify a "far" control tranfers, a 'l' must be prefixed, as in 'ljmp', 'lcall', etc. For example,

GAS syntax			NASM syntax
==========			===========

jmp	*100			jmp  near [100]
call	*100			call near [100]
jmp	*%eax			jmp  near eax
jmp	*%ecx			call near ecx
jmp	*(%eax)			jmp  near [eax]
call	*(%ebx)			call near [ebx]
ljmp	*100			jmp  far  [100]
lcall	*100			call far  [100]
ljmp	*(%eax)			jmp  far  [eax]
lcall	*(%ebx)			call far  [ebx]
ret				retn
lret				retf
lret $0x100			retf 0x100

Segment-offset pointers are specified using the following format:

jmp	$segment, $offset

For example:

jmp	$0x10, $0x100000
If you keep these few things in mind, you'll catch up real soon. As for more details on the GNU assembler, you could try the documentation.

By vivek on 2003-09-01

크리에이티브 커먼즈 라이센스
Creative Commons License