Skip to main content

imageTTFtext 한글 깨짐 해결

· 2 min read

텍스트를 이미지로 만드는 경우에 사용하는 imageTTFtext 함수는 한글이 깨지는 문제가 있다.

해결

imageTTFtext 전에 아래 함수로 한글을 컨버팅해준다.

<?php
/**
* @author http://php.net/manual/en/function.imagettftext.php#57416
*/
function foxy_utf8_to_nce($utf = '') {
if (empty($utf)) {
return($utf);
}

$max_count = 5; // flag-bits in $max_mark ( 1111 1000 == 5 times 1)
$max_mark = 248; // marker for a (theoretical ;-)) 5-byte-char and mask for a 4-byte-char;

$html = "";
for ($str_pos = 0; $str_pos < strlen($utf); $str_pos++) {
$old_chr = $utf{$str_pos};
$old_val = ord( $utf{$str_pos} );
$new_val = 0;

$utf8_marker = 0;

// skip non-utf-8-chars
if ( $old_val > 127 ) {
$mark = $max_mark;
for($byte_ctr = $max_count; $byte_ctr > 2; $byte_ctr--) {
// actual byte is utf-8-marker?
if( ( $old_val &; $mark ) == ( ($mark << 1) &; 255 ) ) {
$utf8_marker = $byte_ctr - 1;
break;
}
$mark = ($mark << 1) & 255;
}
}

// marker found: collect following bytes
if ($utf8_marker > 1 && isset( $utf{$str_pos + 1} ) ) {
$str_off = 0;
$new_val = $old_val &; (127 >> $utf8_marker);
for($byte_ctr = $utf8_marker; $byte_ctr > 1; $byte_ctr--) {

// check if following chars are UTF8 additional data blocks
// UTF8 and ord() > 127
if( (ord($utf{$str_pos + 1}) & 192) == 128 ) {
$new_val = $new_val << 6;
$str_off++;
// no need for Addition, bitwise OR is sufficient
// 63: more UTF8-bytes; 0011 1111
$new_val = $new_val | ( ord( $utf{$str_pos + $str_off} ) & 63 );
}
// no UTF8, but ord() > 127
// nevertheless convert first char to NCE
else {
$new_val = $old_val;
}
}
// build NCE-Code
$html .= '&#'.$new_val.';';
// Skip additional UTF-8-Bytes
$str_pos = $str_pos + $str_off;
} else {
$html .= chr($old_val);
$new_val = $old_val;
}
}
return($html);
}

여담

원작자를 못 찾겠다.. 이걸 만든 사람은 binary 로 말을 할 것 같다.

카카오 og tag 캐시 제거

· One min read

og image 또는 og tag 를 변경하면 페북, 네이버는 시간이 지나면 갱신되나 카카오는 캐싱되어서 바뀌지 않는다. (Description 같은 경우 반영이 되나, Image 는 캐시를 지울 때까지 반영이 안 되는 것 같다)

해결

Kakao Developers에서 캐시를 삭제하여 해결이 가능하다.

Cache 삭제

Cache Tool에서 URL 을 입력하고 캐시를 삭제한다. image from hexo

linkinfo 삭제

카카오 스토리 링크 캐시삭제에서 내 앱으로 인증한 뒤 캐시삭제를 요청한다. image from hexo

Vi, Vim에서 줄번호 표시

· One min read

Vi 줄번호

Vi Editor의 줄번호를 표시해보자

파일을 연 다음 아래 명령어를 입력한다.

표시하기

:set number

image from hexo

추가적으로 라인이동에 필요한 단축키

  • G (shift+g) 문서 맨 끝으로 이동
  • gg (1G) 문서 처음으로 이동
  • {{number}} + G number 번째의 라인으로 이동 (예시 : 300G)

chkconfig run level 설명

· 2 min read

개요

chkconfig 로 부팅시 자동실행 서비스를 등록할 수 있다.

chkconfig service on

이 명령어를 사용하면 2345 레벨이 활성화 된다. 그렇다면 레벨은 뭘까?

Run Level

Run Level 은 서비스의 실행을 단계별로 구분하여 적용하는 것을 말한다.

  • 0 - halt (Do NOT set init default to this)

  • 1 - Single user mode

  • 2 - Multiuser, without NFS (The same as 3, if you do not have networking)

  • 3 - Full multiuser mode

  • 4 - unused

  • 5 - X11

  • 6 - reboot (Do NOT set init default to this)

  • 0 : 시스템 종료시

  • 1 : 싱글 유저 모드 (시스템 복원모드, 기본적으로 관리자 권한의 쉘을 얻게 된다)

  • 2 : NFS가 지원되지 않는 다중 사용자 모드 (네트워크를 사용하지 않는 텍스트 유저 모드)

  • 3 : 완전 다중 사용자 모드 (일반적인 로그인 시, CLI 환경)

  • 4 : 미지정 (사용안함, 임의로 정할 수 있음)

  • 5 : 3번과 같으나 GUI (X11) 환경

  • 6 : 재부팅

모듈 설치시에는 on 또는 345 설정이 큰 차이가 없다.

캐시메모리가 꽉차서 메모리 용량이 부족한 경우

· 2 min read

파일에 접근이 빈번한 시스템에서 메모리 용량을 확인시

## 메모리 용량 확인
$ free -m

캐시메모리의 점유율이 꽉찰 정도로 높게 나타나 메모리 용량이 부족한 걸 확인할 수 있다.

원인

리눅스는 물리적인 저장/통신 장치와 데이터를 주고 받을 때 메모리에 먼저 적재한 후에 데이터를 주고 받는다. 이는 동일한 데이터에 대한 접근을 할 경우 메모리에서 바로 가져오도록 하여 I/O 성능을 높이기 위함이다.

해결

vfs_cache_pressure

시스템 설정 파일을 열어 디렉토리와 inode 오브젝트에 대한 캐시로 사용된 메모리를 반환하는 정도를 지정하는 vfs_cache_pressure 파라미터를 수정해준다.

$ vi /etc/sysctl.conf
## 기본값은 100
vm.vfs_cache_pressure = 10000

cache memory drop

캐시메모리를 주기적으로 비워주자

$ crontab -e
## 매일 새벽 4시에 캐시메모리 강제비우기
0 4 * * * sync && echo 3 > /proc/sys/vm/drop_caches

sync 명령어로 캐시메모리에 담긴 데이터를 실제 저장장치에 반영해주고, drop_caches를 실행한다. 커맨드로 실행시에 메모리를 반환하면서 서버가 잠시 멈출 수 있으니 새벽에 실행을 걸어놓자

  • echo 1 : page cache 해제
  • echo 2 : inode, dentry cache 해제
  • echo 3 : 모두 해제

Linux 유저 비밀번호 변경

· One min read

passwd

리눅스 유저 비밀번호를 변경해보자. 비밀번호를 변경하고 싶은 유저로 로그인을 한 뒤 아래 명령어를 날리면 된다.

passwd

Root 권한이라면 다른 아이디의 비밀번호도 변경이 가능하다.

## passwd 뒤에 유저아이디를 적는다
$ passwd userid

cron 부팅시 프로그램 실행

· One min read

리눅스에서 재부팅시 자동으로 프로그램을 실행해야하는 경우가 있다. init.d에 등록하는 방법이 있지만 스케쥴 작업인 경우 크론에서 관리하는게 깔끔한 것 같다.

예제

$ crontab -e

@reboot /test/test.sh start

@reboot를 쓴 뒤 부팅시 실행시킬 명령어를 적어주면 된다.

내부 아이피 사용 또는 수동 네트워크 설정시 오류

· One min read

수동으로 내부 아이피 세팅 중 문제가 발생하는 경우 확인해봐야한다.

NetworkManager

네트워크 매니저가 돌아가고 있으면 충돌이 발생할 수 있다.

## 확인
$ service NetworkManager status

## 서비스 종료
$ service NetworkManager stop

## 부팅 서비스 삭제
$ chkconfig NetworkManager off

내부 IP 확인

/sbin/ifconfig $1 | grep "inet addr" | awk -F: '{print $2}' | awk '{print $1}'

정상적으로 할당될 것이다.

mysql, maria 등의 서비스 포트 변경이 안 될때

· 3 min read

일반적인 포트 변경

포트 확인

## grep 뒤에 확인할 포트를 적으면 된다.
$ netstat -lp | grep 3307

iptable 수정

$ vi /etc/sysconfig/iptables

## 해당 포트를 방화벽에서 열어준다.
-A INPUT -p tcp -m state --state NEW -m tcp --dport 3307 -j ACCEPT

database 포트 변경

$ vi /etc/my.cnf

## 포트가 설정되있는 부분을 찾아 변경한다.
port = 3307

서비스 재시작

service mysql restart

잘 했는데 서비스가 올라가지 않는다!!!

원인

로그 확인

mysql 설치 경로로 이동하여 로그를 살펴보자.

$ cd /var/lib/mysql/ # basedir 설정이 되어있다면 해당경로를 덧붙힌다.

$ cat {hostname}.err

[ERROR] Cant start server: Bind on TCP/IP port. Got error: 13: Permission denied
[ERROR] Do you already have another mysqld server running on port: 3307 ?
[ERROR] Aborting

해당 포트에 권한이 없다. 해당 포트를 다른 mysqld 서비스가 사용하는가? 라고 로그가 남겨져있다.

SELinux 확인

$ sestatus

SELinux status: enabled

혹시나 역시나 SELinux가 활성화 되어있다. SELinux에서 포트가 서비스용으로 활성화가 되지 않았기 때문에 계속 거절당한 것이였다.

해결

SELinux 설정 확인

semanage 명령어를 사용해서 확인하고 변경할 수 있다. 명령어 실행이 안될 경우 policycoreutils-python 패키지를 설치해주면 된다.

## semanage 설치
$ yum install -y policycoreutils-python

## 포트 확인
## mysql
$ semanage port -l | grep mysqld_port_t
## http
$ semanage port -l | grep http_port_t

mysqld_port_t tcp 1186, 3306, 63132-63164

변경하려는 3307 포트는 등록되어 있지 않다.

SELinux에 포트 등록

semanage port -a -t mysqld_port_t -p tcp 3307

명령어가 iptables에 등록하는 것과 유사하다.

확인

$ semanage port -l | grep mysqld_port_t

mysqld_port_t tcp 3307, 1186, 3306, 63132-63164

이제 mysql restart를 하면 정상적으로 구동된다.

여담

리눅스에서 정상적으로 진행했는데 뭔가 안된다면 SELinux부터 의심해보자.