레이블이 centos인 게시물을 표시합니다. 모든 게시물 표시
레이블이 centos인 게시물을 표시합니다. 모든 게시물 표시

centos bash 4.4 설치

# centos 7.7 사용중인데 bash 최신 버전(4.4이상)을 설치하려고
# yum 으로 시도하면 4.2.46 만 설치된다.
sudo yum install bash

# 때문에 소스를 다운로드 받아 빌드 및 설치해본다.
wget https://ftp.gnu.org/gnu/bash/bash-4.4.tar.gz
tar zxvf bash-4.4.tar.gz
cd ./bash-4.4
./configure
make -j4
sudo make install

# 이제 로그아웃 후 다시 로그인해 버전 확인
bash --version
GNU bash, version 4.4.0(1)-release (x86_64-unknown-linux-gnu)
Copyright (C) 2016 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software; you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

centos 최신 repo 반영하기

# docker등 CentOS 기본 버전에서는 최신 패키지 내용이 반영되어 있지 않다.
# CentOS:7 도커 이미지를 기반에서 nodejs(npm 사용하기 위해) 패키지를 설치할때
yum install -y nodejs

# 다음과 같이 사용 불가능한 패키지로 표시된다.
No package nodejs available

# 이 경우 https://ius.io/ 에서 제공하는 최신 패키지 리스트를 사용하면 된다.
# RHEL(Red Hat Enterprise Linux) 나 CentOS 에 최신 패키지 리스트 적용
# /etc/yum.repos.d/ius.repo 등이 생성된다.
yum install -y https://centos7.iuscommunity.org/ius-release.rpm

# ius 를 추가하면 centos 7 에서 yum 으로 python3 설치할 수 있다.
yum install -y python36u python36u-libs python36u-devel python36u-setuptools

centos git 최신 버전 빌드하기

# redhat, centos 에서 yum 으로 설치되는 git version 은 1.8 정도가 최신이다.
# 그래서 yum 대신 소스를 다운받아 직접 빌드 및 설치를 해야 한다.
https://git-scm.com/download/linux

# git 을 빌드하려면 개발용 curl, perl 이 필요하다.
sudo yum install -y curl-devel perl-devel

# 최신 버전의 소스를 다운받아 빌드 및 설치한다.
wget https://mirrors.edge.kernel.org/pub/software/scm/git/git-2.20.0.tar.gz
tar zxvf git-2.20.0.tar.gz
cd git-2.20.0
make configure
./configure
make -j4 all
sudo make install

# 버전 확인
/usr/local/bin/git version

# 만약 다음과 같이 /usr/bin/git 이 우선한다면
which -a git
/usr/bin/git
/usr/local/bin/git
/usr/bin/git
/bin/git
/usr/local/bin/git

# /usr/local/bin/git 에서 먼저 찾도록 PATH 환경변수를 수정하자.
export PATH=/usr/local/bin/:$PATH


#####


# yum repo 를 추가해서 설치할 수도 있다.
sudo yum install http://opensource.wandisco.com/centos/7/git/x86_64/wandisco-git-release-7-2.noarch.rpm

# git 2.x로 업데이트
sudo yum install git

centos docker 파일 크래시

centos 7 docker 환경에서 컨테이너를 실행 및 접속하여 파일을 삭제(이동)후
ls 명령으로 보면 ? 마크로 뭔가 깨진듯 표시된다.

rm .bash
ls -ahl


파일은 지웠지만 ls 해보면 파일에 접근할 수 없다는 메시지가 발생한다.
cannot access .bashrc: No such file or directory

docker info 로 확인해보면 다음과 같이
d_type=false (linux directory type)로 되어 있고
파일 시스템의 ftype=1 로 변경하라는 경고 메시지가 나온다.

...  중략 ...
Storage Driver: overlay2
 Backing Filesystem: xfs
 Supports d_type: false
 Native Overlay Diff: false
... 중략 ....
WARNING: overlay2: the backing xfs filesystem is formatted without d_type support, which leads to incorrect behavior.
Reformat the filesystem with ftype=1 to enable d_type support.
Running without d_type support will not be supported in future releases.

xfs_info / 으로 확인해보면 현재 ftype=0 인것을 확인 할 수 있다.
... 중략 ...
naming   =version 2              bsize=4096   ascii-ci=0 ftype=0

마운트가 되지 않은 파일에 대해서 다음 명령을 실행해 보자.
mkfs.xfs -n ftype=1 /

실제 / 는 마운트되어 mkfs ftype=1 로 변경을 하지 못했다.ㅠ
하지만 ftype=1 으로 d_type=true 인 새 서버에서는 삭제파일이 ? 로되는 문제는 발생하지 않았다.

# 참고
https://linuxer.pro/2017/03/what-is-d_type-and-why-docker-overlayfs-need-it/

yum 최신 저장소 추가

# yum update 로 패키지를 업데이트를 하더라도 최신 패키지가 반영되지 않을 수 있다.
# 이럴땐 EPEL repository 를 설치하자.
# EPEL(extra package for enterprise linux, fedora 최신 패키지 저장소)
# 저장소 확인
yum repolist

# epel 설치
sudo yum install epel-release

# 혹시 epel 로 기존 패키지 설치가 안되는 경우 epel을 삭제하자
# 현재 설치된 epel 버전 확인
rpm -qa | grep epel-release

# epel 제거 -e 패키지명
sudo rpm -ev epel-release-7-11.noarch


#####

# yum 캐시 전체 삭제
yum clean all

# yum update 했는데 문제가 생긴경우 update 를 되돌려 보자
# yum 으로 실행한 이력을 파악
sudo yum history

# ID 에 해당하는 yum 명령을 undo 한다.
sudo yum history undo ID번호


apache httpd Permission denied, AH00035 에러 해결하기

centos 7 + apache httpd 2.4 로 도커를 구성해 컨테이너 실행시 아파치 웹서버가 기본 설정 동작하도록 하였다.
테스트로 http://localhost:10000 로 접속하니 다음과 같은 에러가 발생하였다.
참고로
로컬 10000 포트와 도커 컨테이너의 80 포트를 연결하였고,
/home/ysoftman/httpd 에 apache httpd 가 구동중이다.


Forbidden
You don't have permission to access / on this server.


도커 컨테이너의 apache httpd error_log 에는 다음과 같이 기록되었다.


[core:error] [pid 56] (13)Permission denied: [client 172.17.0.1:40368] AH00035: access to / denied (filesystem path '/home/
ysoftman/httpd') because search permissions are missing on a component of the path


문제 원인은 httpd 가 실행되고 있는 경로(/home/ysoftman/httpd)가 httpd.conf 에서 다음과 같이 기본 daemon 으로는 실행(접근)할 수 있는 권한이 없어서였다.

User daemon
Group daemon

apache httpd 는 httpd.conf 에서 설정된 User/Group 의 권한으로 실행되는데
내가 만든 계정은 user(ysoftman) group(programmer)로 /home/ysoftman 에서 daemon 계정은 실행할 수 있는 권한이 없다.
namei 로 DocumentRoot 경로를 확인해보면 다음과 같이 경로상의 모든 디렉토리에 x 권한이 있지만 ysoftman 에만 설정되어 있지 않았다.
참고로 namei 프로그램은 경로상의 모든 이름(디렉토리,파일)에 각각에 대해 -m(mode) -o(owner) -l(list format) 로 옵션으로 정보를 보여준다.

namei -mol /home/ysoftman/httpd/htdocs/
f: /home/ysoftman/httpd/htdocs/
drwxr-xr-x root     root       /
drwxr-xr-x root     root       home
drwx------ ysoftman programmer ysoftman
drwxr-xr-x ysoftman programmer httpd
drwxr-xr-x ysoftman programmer htdocs



[해결방법1]
httpd.conf 의 User Group 을 현재 httpd 가 실행되는 /home/ysoftman 에 맞게 변경해주면 된다.

User ysoftman
Group programmer


[해결방법2]
만약 User/Group 을 daemon 을 그대로 사용한다면 다음과 같이 실행권한을 /home/ysoftman 에서 모든 사용자가 실행할 수있도록 실행 권한을 추가하면 된다.

chmod +x /home/ysoftman

확인해보자

namei -mol /home/ysoftman/httpd/htdocs
f: /home/ysoftman/httpd/htdocs
drwxr-xr-x root     root       /
drwxr-xr-x root     root       home
drwx--x--x ysoftman programmer ysoftman
drwxr-xr-x ysoftman programmer httpd
drwxr-xr-x ysoftman programmer htdocs



해결방법1 또는 2를 적용하고 http://localhost:10000 로 접속하면

It works!

centos localtime 변경

# CentOS 의 기본 타임존은 표준시(UTC)로 시간이 표시된다.
# date, ls 등에 나오는 시간은 한국 시간보다 9시간 느리게 표시된다.
# localtime(로컬시간)은 /etc/localtime 을 참조하고 기본 UTC 파일로 링크가 걸려 있다.
# 로컬시간을 서울로 링크하면 한국시간으로 표시된다.
sudo ln -sf /usr/share/zoneinfo/Asia/Seoul /etc/localtime

# 링크 확인
ll /etc/localtime
lrwxrwxrwx 1 root root 30 11월 28 15:40 /etc/localtime -> /usr/share/zoneinfo/Asia/Seoul

centos7 docker 이미지 locale 설정 오류

# centos7 기본 도커 이미지를 받아 실행한다.
# .bashrc 파일에 다음과 같이 언어 설정을 하고 접속을 하게 되면
export LANG=ko_KR.utf8
export LC_ALL=ko_KR.utf8

# 다음과 같이 locale 을 설정할 수 없다는 에러가 발생하는 경우가 있다.
bash: warning: setlocale: LC_ALL: cannot change locale (ko_KR.utf8): No such file or directory

# 사용 가능한 모든 지역 언어(locale -a)설정 리스트를 확인해보면
# 지원되는 언어 3개 밖에 없다.
locale -a
C
POSIX
en_US.utf8

# 언어 패키지가 설치 안된것 같아 다음과 같이 설치해보았지만 설치자체가 안된다.
sudo yum groupinstall korean-support

# 이와 같은 이슈를 고민하는 사람들이 있다.
https://serverfault.com/questions/616790/how-to-add-language-support-on-centos-7-on-docker

# 도커 centos7 최근 이미지에서 영어, c, posix 를 제외한 로케일을 일부러 삭제한것으로 보인다.
# 우선 glibc 패키지를 재설치하라고 했지만 해결되지 않는다.
sudo yum reinstall -y glibc-common glibc

# 해결 방법
# (centos8의 경우) glibc-locale-source 설치
sudo yum install glibc-locale-source

# 이렇게 하면 /usr/lib/locale/locale-archive (locale 이 참고하는 파일)에 추가된다고 한다.
# -f UTF-8 :charmap 지정, /usr/share/i18n/charmaps/UTF-8.gz 심벌, 인코딩 정보
# -i ko_KR : sourcefile 지정, /usr/share/i18n/locales/ko_KR 언어 정의
# ko_KR.utf : 아카이브에 추가할 이름
sudo localedef -f UTF-8 -i ko_KR ko_KR.utf8

# 추가로  UTC 로 설정(링크)되어 있는 링크를 한국시간으로 변경해보자.
https://yoonbh2714.blogspot.kr/2017/11/centos-localtime.html
ln -sf /usr/share/zoneinfo/Asia/Seoul /etc/localtime

# 참고
# centos7 기본이라 패키지가 설치된게 거의 없다.
# dockerfile 로 다음 패키지들은 설치하도록 한다.
# yum 으로 패키지 설치후 locale 이 변경될 수 있어 localedef 는 뒤에 실행 하자.
RUN yum install -y sudo tar git rsync gcc gcc-c++ net-tools which iproute man-pages man setuptool ncurses-devel python-devel libevent-expat-devel bzip2-devel
RUN yum groupinstall -y 'development tools'
RUN localedef -f UTF-8 -i ko_KR ko_KR.utf8 && ln -sf /usr/share/zoneinfo/Asia/Seoul /etc/localtime

# 추가로 
# ubuntu 에서 타임존 설정
RUN apt-get update && \
apt-get install -y rsync apt-utils && \
rm -f /etc/localtime && \
ln -s /usr/share/zoneinfo/Asia/Seoul /etc/localtime

# alpine 에서 타임존 설정
RUN apk --no-cache add tzdata && \
cp /usr/share/zoneinfo/Asia/Seoul /etc/localtime && \
echo "Asia/Seoul" > /etc/timezone

linux write atomic

리눅스에서 멀티 프로세스가 하나의 파일에 쓰기 작업을 할 경우 어떻게 될까?
우선 파일쓰기시 fprintf, fwrite, 등의 C standard library 에서 제공하는 함수를 사용할 수 도 있고 write 와 같은 시스템 함수를 사용할 수 도 있다.
fprintf 의 경우 내부 버퍼링을 하고 write 시스템 콜을 수행하게 된다.

참고

write 함수의 경우 파일이 추가 가능 모드로 열렸다면 파일의 끝 offset 과 쓰기 연산은 atomic 하게 동작한다고 한다.
POSIX.1(.1 은 C standard library 를 규정, .2 shell 관련 규정)에 따라 SSIZE_MAX 까지 쓸 수 있다고 한다. 

SSIZE_MAX 는 /usr/include/bits/posix1_lim.h 에 정의 되어 다음과 같이 정의 되어 있다.
#ifndef SSIZE_MAX
# define SSIZE_MAX  LONG_MAX
#endif

LONG_MAX 는 /usr/include/limits.h 에는 /bits/posix1_lim.h 를 포함하고 있고 다음과 같이 정의 LONG_MAX 가 정의 되어 있다.
#  if __WORDSIZE == 64
#   define LONG_MAX 9223372036854775807L
#  else
#   define LONG_MAX 2147483647L
#  endif

64비트 머신에서 다음과 같이 프로그래밍 해보면
#include <stdio.h>
#include <limits.h>
int main()
printf("SSIZE_MAX : %ld\n", SSIZE_MAX);
return 0;
}

SSIZE_MAX : 9223372036854775807 결과를 보인다.

결국 다음과 같이 write 로 파일 쓸때는 64비트머신에서 거의 무한대로 쓸 수 있는데
On Linux, write() (and similar system calls) will transfer at most 0x7ffff000 (2,147,479,552) bytes, returning the number of bytes actually transferred.(This is true on both 32-bit and 64-bit systems.)

문제는 3.14 이전 커널에서 atomic 하지 않다는 문제가 있다고 한다.

BUGS
Among the APIs subsequently listed are write() and writev(2).  And the effects that should be atomic across threads (and processes) are updates of the file offset.  However, on Linux before version 3.14, this was not the case: if two processes that share an open file description (see open(2)) perform a write() (or writev(2))at the same time, then the I/O operations were not atomic with respect updating the file offset, with the result that the blocks of data output by the two processes might (incorrectly) overlap. This problem was fixed in Linux 3.14.

참고 리눅스 바닐라 커널(kernel) http://man7.org/linux/man-pages/man2/write.2.html

여기서 파일 오동작의 경우가 2개가 있는데
interleave(끼우다) : 데이터 쓰는중에 다른 데이터가 껴들어간것
overlap(겹치다): 데이터를 쓰는중 다른 데이터가 덮어 써지는것
위에서 설명한건 offset 이 atomic 하지 않아 overlap 된다는것.
uname -r 로 확인해보면 3.10.0 버전을 사용하는데 어떻게 될지...?
멀티 쓰레드 환경에서 하나의 파일에 동시 쓰기 테스트

https://github.com/ysoftman/test_code/blob/master/cpp/multi_thread_write_same_file.cpp
로 테스트 하니 멀티쓰레드에서는 문제가 없고 멀티 프로세스 환경에서 fprintf()를 사용시문제가 발생한다.

리눅스 버전 의미 참고 http://unix.stackexchange.com/questions/9743/numbering-convention-for-the-linux-kernel

테스트 환경은 centos7 이고 커널버전은 3.10.0-514.6.2.el7.x86_64
centos 에서는 기본 리눅스 바닐라 커널(3.10.0)을 베이스로 하고 이슈가 발생된 부분은 패치 적용하는 방식을 취한다고 한다. 그래서 3.10 버전이지만 위와 같은 오래전 이슈는 이미 수정되어 반영된것으로 보인다.

Linux hostname 설정하기

# 현재 hostname 확인

hostname



# hostname 설정 방법1(임시, 재부팅하면 원래대로 돌아감)

sudo hostname ysoftman_hostname





# hostname 설정 방법2(임시, 재부팅하면 원래대로 돌아감)

sudo 가 아닌 root 로그인에서

echo "ysoftman_hostname" > /proc/sys/kernel/hostname





# 부팅시 hostname 설정되도록 하려면 파일에 설정하도록 한다
# centos6

sudo vi /etc/sysconfig/network

HOSTNAME=ysoftman_hostname


# centos7

hostnamectl set-hostname ysoftman_new_hostname
# 확인
hostnamectl status