롯뽄기힐즈 안내도.



롯뽄기 힐즈의 상징
높은 건물들 때문에 그늘이 져서 사진이 어둡게 나왔다.








시부야로 가기 위해서 버스 정류장에서 휴식. 우리나라와는 다르게 사람들이 줄을 서있다.
우리나라같았으면 버스탈때 전쟁일텐데 ㅋㅋ


버스안에 불꽃놀이 광고. 저녁에 이 불꽃놀이를 보러 간다.


시부야 도착. 엄청난 인파들. 날씨도 더운데 사람들 까지 많으니 정말 돌아다니기 힘들었다.


영화로 유명한 하찌동상. 시부야 역앞에 있다.
ㅋㅋ근데 정말 10초 감동. 그 이후론 이게 뭐지? ㅋㅋ 일본인들이 이 동상앞에서 약속을 많이 잡는다고 한다.



시부야 역 앞.




시부야에서 유명한 109 건물 ㅋ



시부야에서 먹은 점심.
덮밥인데 맛있다. 일본의 김밥천국 같은데서 먹었다.



일본 전통 의상 입고 호객질.

긴자에 있는 소니프라자. 깔끔하다.


소니샵은 일정 기간마다 특정 테마가 있다고 한다.
오늘은 아쿠아 테마.




3D 티비 전시관. 안경을 쓰고 보니 좀 신기했는데 ㅋㅋ
굳이 티비보는데 이거까지 쓰고 보긴 귀찮다.



소니에릭슨의 엑스페리아
일본의 NTT도코모에서 밀어주고있는 스마트폰.
한국에서는 아이폰의 대항마가 겔럭시S이듯이, 일본에서는 아이폰 대항마가 요놈 처럼 보였다.


미친듯이 비싼 바이오 넷북.
이해할수 없는 가격.. 이쁘긴한데 이거 살빠엔 N5를 산다.


긴자오면 다들 한번씩 먹어봐야 한다는 와플.
진짜 맛있더라 ㅋㅋ말그대로 꿀맛.



일본 택시.
일본 택시는 전부 저렇게 클래식한 모양인데.
전부 새차같다. 저런 디자인으로 새차가 나오는건가.


일본의 신기한 버스. 이 날 엄청 더웠는데 저사람들 ㅋㅋ죽을것 같은 표정들이였다.


긴자의 상징




닛산 컨셉카.


긴자의 애플샵. 애플 건물 정말 심플하게 생겼다.



아이폰4


화면 정말 깨끗했다. 이게 잡스횽이 말한 레티나 액정ㅋ
근데 실제로 보니 슈퍼아몰레드보단 못한 듯. 하지만 해상도가 좋아서 글자 보기엔 아이폰4가 훨씬 깔끔하고 좋은 느낌인듯 했다.





아이폰4에 ㅋㅋ누가 네이버를 이미 사파리로 접속한 기록이.
한국인들 정말  많은 것  같다.


아이패드.
정말 무겁다. 여자들은 백 안에 넣고 다니기 부담스러운 무게같다. 하지만 일본애들 많이 들고 다니더라.
전철안에서도 아이패드에 만화넣고 보는 사람들을 심심치 않게 볼 수 있다.






맥북과 아이팟 터치, 나노


애플샵 내부. 뉴욕에 있는 애플샵이랑 비슷한 느낌.



일본은 주말마다 보행자 천국이라고 해서 이런 넓은 도로에 차를 못다니게 한다.
도로 중앙에 커피 마실 수 있는 테이블이 있다. 하지만 더워서 ㅋㅋ앉아서 마시기 싫다.





부산 -> 도쿄(나리타) 오후 2시 15분 비행기(JL 958편)


인터넷으로 다운받은 하나은행 환전 우대권을 이용해서 약 만5천원정도 절약.
8만엔 환전하는데 우리나라 돈으로 한 110만원정도 들었다.


드디어 김해 공항 도착 ㅋㅋ
김해공항 국제선 청사 진짜 작은것 같다. 근데 건물은 깨끗하고 좋았다.
태어나서 처음 가본 공항.


티케팅하는데 시간이 남아 있어 김해 공항내의 스타벅스에서 아메리카노 한잔.


스타벅스 창가에서 보이는 국내선 청사.


내가 탈 비행기 티케팅이 시작되었다.



내앞에 있던 일본 노인네인데.
티케팅 기다리는 시간 틈틈히 저렇게 독서를 하고 있었다.
일본이 강대국인 여러가지 이유 중 하나..


티켓 발권을 완료.
병특이라 1회용 여권ㅋㅋ



검역, 세관신고, 보안검색, 출국심사를 무사히 통과하고 ㅋ
격리대합실에서 대기 중.
비행기 이렇게 가까이서 본건 처음인데 별시리 감동은 없었다.



내가 탑승할 4번 게이트


나를 도쿄로 될고 갈 비행기.
저기 멀리서 내가 맡긴 짐을 비행기 안에 싣고 있는걸 보았다.


비행기 탑승시간에 맞추어서 탑승.
비행기 첨탄다고 일부러 창가에 앉았는데 ㅋㅋ
엔진 옆이라 엄청 시끄럽다.







창 밖 풍경. 아 진짜 예술이다.
이렇게 높은데서 처다보는건 처음인데.







기내식인데 은근히 먹을만 하다.



한시간을 넘게 가자 일본 열도가 보였다.



정신이 없어서 일본 입국할땐 사진을 못찍었다. ㅋㅋ
나리타 공항안에 케이세이버스 카운터에서 카히인 마쿠하리 역까지 가는 티켓을 1,100엔에 구입했다.
놀랜게 은근히 공항 내에 영어가 잘 통한다는 것 ㅋㅋ


일본 도착하자 마자 처음 먹은 음식.
카이힌마쿠하리 역앞에 있는 스시집.
한국 롯데 백화점에서 먹던 비싼 스시랑은 수준이 다르다.
돈은 그때 반정도 인거 같은데. 정말 신선하고 맛있었다.


절대로 ㅋㅋ난 덕후가 아니지만
덕후 체험.
돈키호테라는 잡물건 파는 가게. 나미양과 함께.ㅋㅋ하악하악 ㅋㅋㅋ
아 진짜 변태 같애.



거래량 없는 전고점 돌파

전고점을 돌파하기 위해선, 저가에 매수한 이익실현 매물과 전고점에 물려있는 악성매물을 모두 소화할 수 있는 강력한 신규 매수세가 들어와야 한다.

이러한 매물 소화과정은 반드시 거래량 증가를 수반하는게 일반적이고, 통상 전고점대의 거래량보다 더 많은 거래량이 터지게 됩니다.

그런데 밑의 종목 A부분처럼 거래량이 터진 전고점대에 임박하고 돌파하는 시점에서 특별히 거래량 급증이 없는 종목이 있습니다.

전고점을 돌파하기 위해선 거래량이라는 에너지의 증가가 필요한데, 거래량 증가가 없는데도 주가가 밀리지 않고 오히려 꾸준히 상승하는 종목들이 있는데, 도대체 그것은 무슨 이유 때문일까요?

정답은 전고점에서 매수했던 세력이 지금 주가를 상승시키는 세력과 동일하기 때문입니다.

즉 전고점가격대에서 물량을 처분하지 않기 때문에 거래량 증가 없이 전고점 가격을 돌파하게 되는 것입니다. 통상 전고점대에 물려있는 매물을 새로운 신규매수세가 매도물량을 소화하면서 손바뀜 과정이 발생하고 이로 인해 거래량이 터지게 되는데, 어떠한 세력이 주가를 상승시킬 의도로 매집한 경우에는 자신이 매물을 내놓지 않는 한 전고점대에 임박해서도 거래량은 증가하지 않게 되는 것이다.

다시 말하면 전고점에서 매집한 세력은 일시적으로 주가가 밀렸다가 다시 전고점 가격에 도달해도 원래 자신이 계획한 이익실현 가격대가 아니므로 매도하지 않고 이로 인해 거래량의 증가가 없다는 점입니다.

결국 중요한 것은 이렇게 세력이 매집하여 전고점 가격대에서 이익실현을 하지 않았다는 것은 세력이 주가를 더 상승시키겠다는 의도이므로 앞으로 주가가 추가적인 상승할 가능성 매우 높은 종목이 된다는 점입니다.


* 지지선 무너지면 팔아라
흔히 단기 급증한 종목의 상투시점은 거래량이 폭증한 시점으로 대충 파악할 수 있다.

즉 거래량 상투는 주가 상투다. 그러나 실전에서 종종 단기 급등한 종목임에도 거래량 폭증없이 주가 상투가

만들어지고 이후 주가가 지속 폭락하는 경우가 있다.

주식공부를 어느 정도 한 분들은 단기 급등주에서 거래량 폭증이 나오면 세력이 이탈한 것으로 보고, 거래량

폭증이 없으면 세력이 아직 잔존해 있는 것으로만 믿고 지지선이 무너지는데도 그냥 종목을 들고 있다가 끔찍한

결과를 맞게 되는 경우가 있다. 물론 거래량 폭증으로 세력이탈 여부를 체크하는 것은 중요하나, 거래량만으로

모든 매매판단을 다 해서는 안된다는 점을 말씀 드리고 싶습니다.

주가를 단기에 급등시킨 세력이 이탈하는 차트유형은 하루 변동폭이 커져 캔들 길이가 길어지고 거래량이 폭증

하는 것이 일반적입니다.

그러나 밑의 종목처럼 거래량 급증없이 조용히 빠져나가지 않았으니 다시 들어올 것이라는 원칙 아닌 집착만을

가지고 지지선이라 할 수 있는 20일선을 주가가 깨고 내려가는 데도 그저 들고만 있는 분들은 하나만 알고 둘은

모르는 분들이라 할 수 있다.   그 둘이란 눈에 보이지 않게 서서히 빠져나가는 세력도 있을 수 있고, 세력이라고

반드시 모두 이익을 다 내는 것은 아니란 점입니다.


* 장대양봉후 거래량없는 단봉
주가가 바닥권이나 상승폭이 적은 상태에서 갑자기 대량 거래량이 터지면서 장대양봉이
나오면 일단 주목해야

합니다. 거래량이 급증하면서 장대양봉이 나왔다는 것은 강한 매수세력이 개입되었을 가능성이 매우 높기 때문

입니다. 일시적 호재성 뉴스에 의한 거래량급증과 장대양봉은 제외하고 순수하게 차트만으로 거래량이 급증하고

장대양봉이 나온 종목중 그 다음날 주가가 어떠한 흐름을 보이는지를 수급적인 측면에서 체크하는 것이 중요하다. 

 예를들어 전날 강하게 매수해서 장대양봉을 만든 세력이 다음날 다시 강하게 매수를 한다면 그 종목은 연속해서

장대양봉을 만들면서 강한 주가상승을 할 가능성이 높습니다.

반대로 장대양봉을 만든 세력이 다음날 아침에 주가를 갭상승시킨 이후 바로 이익실현에 나선다면 장대음봉이

만들어지게 됩니다.

세번째로는 전일 강하게 매수했던 세력이 잠시 매수를 쉬는 유형으로 장대양봉이후 세력이 다른 이익실현 매물만을

소화할 뿐 주가를 끌어 올리기 위해 적극적으로 매수를 하지 않는 형태입니다.  밑의 그림처럼 장대양봉이 나온 이후

 2~4일 정도 주가가 옆으로 횡보하는 모습이 나오면서 거래량이 급감하고 주가의 변동폭이 작은 단봉 캔들이  나온

다면 일단 주가를 급등시킨 세력이 차익매물을 소화하는 과정에 있을 확률이 높으므로 일단 관심을 갖는 것이 좋다. 

그러다가 주가가 밀리지 않고 다시금 거래량이 증가하면서 장대양봉이후 나온 가격대를 돌파할때 함께 매수한다면

효과적인 매매가 될 수 있습니다.


이평선이 지지선 또는 저항선 역할을 하는 원리를 통해 알아봅니다.

5일선이란?

5일 종가의 이동평균선, 다른 의미로  5일동안 시장에 참여한 참여자의 평균매수가

 

20일선이란?

20일 종가의 이동평균선, 다른 의미로  20일 동안 시장에 참여한 참여자의 평균매수가

 

이동평균선은 현재 주가의 위에 있느냐? 아래에 있느냐?에 따라, 그 의미와 해석이 달라집니다.

 

현재 주가가 20일 이동평균선 아래 있다면, 20일 동안 시장에 참여한 투자자들이 손실을 본 상태

다시 말하면 지금 물려 있으니 자기가 샀던 가격으로만 오면 던질려고 준비중입니다.

 

, 현재 주가 위에 있는 이평선은 매도 대기세력, 그래서 일반적으로 저항선이라고 합니다.

 

반대로 말하면,

 

현재 주가가 20일 이동평균선 위에 있다면 20일 동안 시장에 참여한 투자자는 수익이 나고 있는 상태

주가가 하락을해서 다시 20일 이동평균선에 닿게 된다면 자기들이 샀던 가격에서 상승의 경험이 있는 투자자, 혹은 지난번에 그 가격에서 못 샀던 아쉬움이 있는 투자자들은 자기들이 싸다고 생각한 주가로 다시 왔기 때문에, 또 상승을 경험한 가격에 왔기 때문에 매수욕구가 본능적으로 발동하면서 한번 더 상승할 것이라는 예측으로 매수를 준비합니다.

 

즉, 현재 주가 아래에 있는 이평선은 매수 대기세력, 그래서 일반적으로 지지선이라고 합니다.

 

지금 여러분들이 가지고 있는 종목의 현재 주가 위에는 무엇이 있습니까? 혹시 20일선이 있습니까?

그럼 20일 동안 물려 있는 사람들의 심정을 헤아려 보세요.

 

현재의 주가 아래에 무엇이 있습니까? 혹시 20일선이 있습니까?

그럼 20일 동안 수익을 냈던 사람들의 심정은 어떨까요?

 

현재 주가와 이평선에 숨겨진 시장 참여자들의 심리를 분석하면서 주식을 바라보면 더 재미있어집니다.

 

주식투자를 즐기세요.


출저 : http://stock.daum.net/item/bbs.daum?code=046890&viewObj=1:2:0&nil_profile=stockprice&nil_menu=itemdebatemore



아놔...

'It`s me.' 카테고리의 다른 글

자신이 슬럼프에 빠졌다고 생각하시는분들을 위한....  (0) 2010.12.22
티스토리 초대장 12장 배포합니다.  (25) 2010.09.17
사과밭ㅋㅋ  (1) 2010.07.12
Dick in a box.  (0) 2010.07.04
드라마 <카이스트> 中  (0) 2010.06.23
매수시 확인해야 될 사항
현재 시장이 좋은가?
망할 가능성이 없는 우량주인가?
상승파동인가?
쌍바닥인가? 바닥이 확인 되었는가?
월봉, 주봉, 일봉상 지저대 저항대를 확인했는가(손절라인 정하기)?
반드시 분할 매수 1/3씩 하는가?
욕심을 부리고 있지 않은가?
전 고점을 강하게 뚫고 지지하는가?


매도시 확인해야 될 사항
하락파동인가?
20일선을 하락 돌파하는 외봉이 나왔는가?
(보수적인 접근시 10일선)
심리적으로 마음이 불안한가?
지지라인이 깨졌는가? 손절라인 지키기


개미들이 이기는 방법
신용, 단기자금 자재, 재무재표 확인, 성장성 확인등의 조건들만 충족시킨다면
단기적으로 매물대 저항이던, 수급이 꼬이던 견디면 반드시 승리하게 되어있다.


여권도 없는 내가 무턱대고 인터파크에서 부산-나리타행 비행기 티켓을 지르고 말았다.
출국 일주일전까지 여권정보를 입력하면 된다고 하는데.
비행기 표 정말 비싸다. 사장님이 허락 안해주시면 말짱 꽝인데 ㅋㅋㅋ



병특은 해외여행가기 힘들 줄 알았는데, 생각보다 절차가 간단하다. ㅋㅋ
다만 업체 사장님의 동의가 필요하다.
사장님이 동의해주지 않으면 죽어도 못간다.
우리 사장님은 좋으신 분이라 쿨하게 9일 휴가를 받아냈다. -_-)b


병특이 국외 여행을 하기 위해서는 국외여행 허가신청서, 소속기관의 장의 추천서 이 2가지가 필요하다.
경우에 따라서는 소속기관장의 추천서만 있어도 된다(부산 병무청에서는 소속기관장 추천서만 있으면 된다고 했지만 난 2가지 다 보냈다).

아래의 URL에서 국외 여행 허가 신청서, 소속기관장의 추천서 양식을 다운받는다.
http://www.mma.go.kr/kor/s_navigation/travel/travel02/travel022/index.html


국외여행허가신청서, 소속기관장추천서를 작성후 회사 직인을 찍고 스캔한다.



아래의 사이트에서 국외여행허가 신청을 클릭하고 해당 양식에 맞게 작성한다.
스캔 한 파일을 첨부하면 보통 1~2시간 안에 병무청에서 국외 여행이 허가되었다고 문자가 날라온다.
나같은 경우는 30분도 안되서 처리됐다고 문자고 오더라. 처리 결과 또한 아래의 사이트에서 확인하면 된다.
http://www.mma.go.kr/kor/s_minwon/subscribe/subscribe05/index.html

여권만들 때 "여권발급용 국외여행 허가서"를 반드시 가져가야 하기 때문에 국외여행허가서/증명서를 조회해서 출력을 해두워야 한다.


사과에 불들어온거봐 ㅋㅋㅋㅋㅋ
어디지 학교 세미나실같은데 ㅋㅋㅋ
당당하다  ACERㅋㅋㅋ

'It`s me.' 카테고리의 다른 글

티스토리 초대장 12장 배포합니다.  (25) 2010.09.17
이들에겐 공통적인 고민이 있다. ㅋㅋㅋ  (0) 2010.07.21
Dick in a box.  (0) 2010.07.04
드라마 <카이스트> 中  (0) 2010.06.23
블로그 이사했습니다.  (0) 2010.05.10
오랜만에 신선한 충격을 준 Dick in a box. ㅋㅋ 이런걸 생각하는 미국인이란 ㅋㅋㅋ
정말 신선하다.

오래된 연인이면 특별한날.
분위기 잡고 "Take a look inside, its my dick in a box".  하면 재미있을 듯.





Hey girl, i got somethin' real important to give you

so just sit down and listen

Girl You know we've been together for such a long long time (such a long time)

But now I'm ready to lay it on the line (Wow!)

You know its christmas,

and my heart is open Wide (open wide)

Gonna give you something so you know whats on my mind (whats on my mind)

A Gift real special, so take of the top

Take a look inside, its my dick in a box (its in a box)

Not gonna get you a diamond ring

That sorta gift don't mean anything

Not gonna get you a fancy car

Girl you gotta know you're my shining star

Not gonna get you a house on the hills

Girl like you needs something real

Wana get you something from the heart (Something Special Girl)

its my dick in a box, my dick in a box babe

Its my dick in a box (oooh), my dick in a box girl

See im wise enough to know when a gift needs given (girl)

and i got just the one

something to show you that you are second to none (yeah, yeah yeah)

To all the fellas out there with ladies to impress
ITs easy to do just follow three steps

1. Cut a hole in a box

2. Put your junk in that box

3. Make her open the box

and thats the way you do it

its my dick in a box, my dick in a box babe

its my dick in a box (oooh)

my dick in a box girl

Christmas.. dick in a box

Haunnuka.. dick in a box

Kwanza... a dick in a box

every single holiday a dick in a box

over at your parents house a dick in a box

mid-day at a grocery store a dick in a box

backstage at the CMA's a dick in a box (yeah wow wow wow wow wow)

(a dick in a box)

(a dick in a box)

(a dick in a box)


'It`s me.' 카테고리의 다른 글

이들에겐 공통적인 고민이 있다. ㅋㅋㅋ  (0) 2010.07.21
사과밭ㅋㅋ  (1) 2010.07.12
드라마 <카이스트> 中  (0) 2010.06.23
블로그 이사했습니다.  (0) 2010.05.10
Visual Studio 2010 사용기  (0) 2010.04.20
            int start = System.Environment.TickCount;
System.Threading.Thread.Sleep(666);
int end = System.Environment.TickCount;
Console.WriteLine("측정 시간 : {0}ms", end - start);
Console.ReadLine();


실행 결과
측정 시간 : 667ms

거의 1~2ms 정도의 오차로 측정되고 있다.
닷넷프레임워크 2.0이상에서는 Stopwatch 클래스를 이용하면 손쉽게 시간을 측정할 수 있지만
이 방법도 여러모로 쓸모가 많은 것 같다.

StopWatch 사용법
http://kworks.tistory.com/99

티스토리에서 SyntaxHighlighter 사용하는 방법

SyntaxHighlighter 다운로드
http://alexgorbatchev.com/wiki/SyntaxHighlighter:Download

다운로드 후 압축을 풀면 scripts, src, styles디렉토리가 생성된다.

Tistory 관리자 화면에서 스킨 -> HTML/CSS편집 으로 들어간다.
파일 업로드를 이용해서 scripts, src, styles 디렉토리 안의 모든 파일들을 업로드 한다(이때 자동으로 tistory 계정의 images 디렉토리로 업로드된다).

HTML/CSS 편집에서
<head>와 </head>사이에 아래의 내용을 복사해서 붙여넣는다.
<!-- code syntaxhighlighter -->
<script type="text/javascript" src="./images/shCore.js"></script>
<script type="text/javascript" src="./images/shBrushCpp.js"></script>
<script type="text/javascript" src="./images/shBrushCSharp.js"></script>
<script type="text/javascript" src="./images/shBrushPhp.js"></script>
<script type="text/javascript" src="./images/shBrushJava.js"></script>
<script type="text/javascript" src="./images/shBrushJScript.js"></script>
<script type="text/javascript" src="./images/shBrushXml.js"></script>
<script type="text/javascript" src="./images/shBrushCss.js"></script>
<link type="text/css" rel="stylesheet" href="./images/shCore.css"/>
<link type="text/css" rel="stylesheet" href="./images/shThemeFadeToGrey.css"/>
<script type="text/javascript">
SyntaxHighlighter.config.bloggerMode = true;
SyntaxHighlighter.config.clipboardSwf = './images/clipboard.swf';
SyntaxHighlighter.all();
</script>
<!-- code syntaxhighlighter -->

테마 변경시 위의 script중에 <link type="text/css" rel="stylesheet" href="./images/shThemeFadeToGrey.css"/> 이 부분을 수정한다.
참조 : http://alexgorbatchev.com/SyntaxHighlighter/manual/themes/

이제 블로그에서 글을 작성할 때 소스코드 부분은 사용언어에 맞게 HTML모드에서 아래와 같이 적어주면 된다.
<pre class="brush: c-sharp;">
... source code ...
</pre>

브러쉬 목록
분류 사용가능 brush명 
필요 파일
Bash/shell bash, shell shBrushBash.js
C# c-sharp, csharp shBrushCSharp.js
C++ cpp, c shBrushCpp.js
CSS css shBrushCss.js
Delphi delphi, pas, pascal shBrushDelphi.js
Diff diff, patch shBrushDiff.js
Groovy groovy shBrushGroovy.js
JavaScript js, jscript, javascript shBrushJScript.js
Java java shBrushJava.js
Perl perl, pl shBrushPerl.js
PHP php shBrushPhp.js
Plain Text plain, text shBrushPlain.js
Python py, python shBrushPython.js
Ruby rails, ror, ruby shBrushRuby.js
Scala scala shBrushScala.js
SQL sql shBrushSql.js
Visual Basic vb, vbnet shBrushVb.js
XML xml, xhtml, xslt, html, xhtml shBrushXml.js


실제 사용 예
function test() : String
{
	return 10;
}
// 출력
int ViewMessage(char *msg)
{
        printf("%s\n", msg);
}
프로그램을 하다 보면 enum이나 sturct 데이터형에 null을 넣어서 초기화를 하고 싶을 때가 있다.
이 방법을 알기전까진 -9999이나 0처럼 쓰이지 않는 값을 NONE에 넣어서 초기화를 했는데, 그럴 필요가 없다.
모르면 손발이 고생.

C#에서 Value형태의 데이터형에 null 데이터를 넣을 수 있는 방법을 제공한다.
이 방법은  .net framework 2.0이상에서만 사용할 수 있다.

        enum Color
        {
            RED = 0x39,
            GREEN,
            BLUE,
        }

        Nullable<Color> whatColor = new Color();
        //whatColor = Color.GREEN;
        whatColor = null;

        if (whatColor != null)
        {
                Console.WriteLine(whatColor);
                Console.WriteLine(Enum.Format(typeof(Color), whatColor, "g"));
                Console.WriteLine(Enum.Format(typeof(Color), whatColor, "G"));
        }
        else
        {
                Console.WriteLine("whatColor variable is null.");
        }



     enum Color
        {
            RED = 0x39,
            GREEN,
            BLUE,
        }

----------------------------------------------------------------------------------------------

        Color whatColor = Color.GREEN;

        Console.WriteLine(whatColor);
        Console.WriteLine(Enum.Format(typeof(Color), whatColor, "g"));
        Console.WriteLine(Enum.Format(typeof(Color), whatColor, "G"));

        Console.WriteLine(Enum.Format(typeof(Color), whatColor, "d"));
        Console.WriteLine(Enum.Format(typeof(Color), whatColor, "D"));

        Console.WriteLine(Enum.Format(typeof(Color), whatColor, "x"));
        Console.WriteLine(Enum.Format(typeof(Color), whatColor, "X"));

        Console.WriteLine(Enum.Format(typeof(Color), whatColor, "f"));
        Console.WriteLine(Enum.Format(typeof(Color), whatColor, "F"));

결과
GREEN
GREEN
GREEN
58
58
0000003A
0000003A
GREEN
GREEN

계속하려면 아무 키나 누르십시오 . . .



가끔 enum 데이터 타입의 값을 문자열로 출력할 일이 있는데 이 방법을 이용하면 쉽게 해결된다.


참고 :
  http://msdn.microsoft.com/ko-kr/library/system.enum.format%28VS.90%29.aspx
  http://msdn.microsoft.com/ko-kr/library/system.enum.getname%28VS.90%29.aspx


김주혁 : 정만수 학부 때 성적이 좋았습니까?

이휘향 : 나빴어. 왜?

김주혁 : 아, 그럼 면접을 잘 본 모양이지요.

이휘향 : 형편없었어.

김주혁 : 그...래요?

이휘향 : 그런데 어떻게 대학원에 왔냐구?

김주혁 : ..예..

이휘향 : 학부때 실험을 하나 시킨게 있어.

            열 일곱번 실패를 하더라구.

            남들 세 번이면 완성할 걸 열 일곱번이나.

            그리고 두 달만에 해냈어.

            그게 중요한거야.

            연구란건 성적이 좋은 사람이 하는게 아니야.

            끝까지 포기하지 않는 사람이 하는거지.

            무슨 말인지 알겠어?

 

 

 

드라마 <카이스트> 中

'It`s me.' 카테고리의 다른 글

사과밭ㅋㅋ  (1) 2010.07.12
Dick in a box.  (0) 2010.07.04
블로그 이사했습니다.  (0) 2010.05.10
Visual Studio 2010 사용기  (0) 2010.04.20
peeping life  (0) 2010.01.14
로드가 많은 환경에서 메모리 부족 예외가 발생할 수 있다.
이는 .NET 가비지 컬렉터(GC)가 항상 메모리를 dispose하지 않기 때문에 발생할 수 있다.

이 문제를 해결하기 위해서 빈번하게 GC.WaitForPendingFinalizers 메서드를 직접 호출해야 한다.

참고 GC.WaitForPendingFinalizers 메서드를 직접 호출하는 응용 프로그램은 성능이 저하될 수 있다.


출저 : http://support.microsoft.com/kb/912884


 * Comment : General form of words sequence in a sentence
      -> Subject + verb + object (adjective+noun)  +  adverb( location + time )
      -> who + action word + what + how + where + when
                                                = how(where + when)

For example :
Who + action word + what                 +  where         + when
I      + ate              + a fried chicken  +  in my home  + yesterday.


'English' 카테고리의 다른 글

I have p.p.  (0) 2010.10.01
한국인들이 어려워하는 미국 영어 발음법칙 35개!  (0) 2010.09.28
독해를 잘 하기 위한 조언  (1) 2010.09.28
ed의 발음  (0) 2010.09.28
영단어 100  (0) 2010.08.30
예전에는 이런 일이 없었던 것 같았는데. 어느순간부터 노트북 어뎁터에 연결이 되어있는 데도 불구하고
노트북 동작 클럭이 2Ghz에서 999Mhz로 설정되어 동작하고 있었다.
이게 노트북이 베터리 모드일때 전기 아낀다고 낮은 클럭으로 사용하게 하는 기능이 켜진것 같은데
전기를 배불리 먹여줘도 풀리지가 않으니..
이거 뭐 컴파일 하는데도 엄청 오래 걸리고 마우스도 뚝뚝 끊기고.
아무튼 아래의 방법으로 말끔하게 해결됐다.


제어판 -> 전원옵션 -> 전원 구성표에서 "항상켜기" 선택


언젠가부터 아이디를 Kei로 바꿔쓰기 시작했는데, 블로그 도메인 또한 바꾸고 싶었다.
꾸준히 내 블로그에 들어오는 사람들도 있는것 같고 해서 도메인 바꾸는게 쉽지가 않았다.
그래도 아직까진 방문자 규모가 작기 때문에 ㅋㅋ
더 많아지기 전에 바꾸기로 결심.
데이터야 티스토리 횽의 백업 기능 덕분에 쉽게 옮길 수 있었고.
새집 이사왔으니깐 새로운 기분으로 열심히 해보자!



'It`s me.' 카테고리의 다른 글

Dick in a box.  (0) 2010.07.04
드라마 <카이스트> 中  (0) 2010.06.23
Visual Studio 2010 사용기  (0) 2010.04.20
peeping life  (0) 2010.01.14
2009 개발 언어 순위  (2) 2009.12.13
Visual Studio 2008 나온지 얼마나 되었다고 2010이 나오는 것이냐 ㅋ
이 자비를 모르는 MS 같으니라고.
아직도 주변에는 출시 된지 10년이 넘은 Visual Studio 6.0(98년도 출시)쓰는 분들도 있는데 ..

어찌됐든 실무에서도 사용 가능한지 테스트도 해볼 겸 한번 사용해보기로 했다.

옛날하고 다르게 전세계 대학생이면 누구든지 무료로 다운로드 받을 수 있다(통큰 MS형님들. 예전같았으면 어둠의 경로로 이런개발툴 받으러 다닌다고 고생좀 했을 텐데. 정상적인 방법으로 좋은 툴들을 받을 수 있다니 정말 세상 좋아졌다).

나도 겉은 ㅋㅋㅋ 대학민국 대학생이기 때문에 MS Dreamspark 사이트에서 Visual Studio 2010을 무료로 다운로드 받을 수 있었다(대학생이 맞는지 확인 절차가 필요한데 이는 본인이 다니는 대학교의 이메일 계정만 있으면 된다. 예전엔 국제 학생증으로 본인 인증을 해야 되는걸로 기억나는데. 아무튼 절차가 엄청 간단해졌다).


Dreamspark 사이트에서 대학생 인증만 끝나면 MS에서 출시된 거의 모든 개발툴들을 무료로 다운로드 받을 수 있다(Windwos Embedded CE 6.0도 받을수 있구나 ㅠ). 시디 이미지 형태로 배포를 하는데 데몬으로 읽어서 설치하면 된다.

Visual Studio 2008 설치 모습이랑 비슷하다.
아직 .NET Framework 2.0도 잘 사용못하는데 4가 나오면 어쩌겠다는거니 ㅠ WPF도 구경도 못해본 나인데..



아래는 Visual Studio 2010 Professional을 시작하는 모습이다. 이전 버전보다 VS로고와 Splash 화면이 매끈하고 섹시해졌다ㅋ


기본 환경 설정창도 VS2008이랑 비슷하다. 난 C#환경이 편하니깐. 이걸로 선택.

기본 시작화면. VS2010은 WPF를 이용해서 만들었다고 들었는데 화면 자체가 디게 부드러워진것 같다. 기분탓인지 2008보다 반응속도가 빠른것 같은데..아무튼 전체적으로 화면이 화사하다.


실제 코드 에디터 창(C#, MFC)


잠깐 써보고 느낀건데 ㅋ 2008이랑 별반 다를 것도 없고 실무에 바로 적용 가능할 것 같다.
2008 버그들이 많이 고쳐졌다고 하는데
가장 눈에 띄게 좋아진점은 C++에서도 C#처럼 실시간으로 문법 체크가 된다는 것이다.
2008까지는 한번 컴파일 해줘야 인텔리전트 기능도 써지고 하던데..
암튼 이것 말고도 좋아진 점이 엄청 많은 것 같다. 추가된 콤포넌트들도 많고 .
가면 갈수록 개발 환경이 편해지는구나~~


'It`s me.' 카테고리의 다른 글

드라마 <카이스트> 中  (0) 2010.06.23
블로그 이사했습니다.  (0) 2010.05.10
peeping life  (0) 2010.01.14
2009 개발 언어 순위  (2) 2009.12.13
더디어 성공.  (1) 2009.11.03
문자열 처리와 관련된 윈도우 매크로이다.
유니코드를 사용할 경우에는 컴파일할 때 TEXT("문자열")이 L"문자열"로 변환된다.
유니코드를 사용하지 않을 경우에는 "문자열"로 변환된다.
따라서 TEXT()매크로를 사용하면 유니코드를 사용 유무에 상관없이 문자열을 처리할 수 있다.

* LPCTSTR 자료형 : char* 나 wchar_t*로 변환된다. 즉 유니코드를 사용할 경우엔 wchar_t*로 변환, 사용하지 않을 경우엔 char*로 변환된다.

MFC에서 CWnd 클래스는 모든 윈도우 클래스의 기본(Base) 클래스.
CWnd 클래스는 모든 MFC클래스의 부모라 불리는 CObject 클래스와 CCmdTarget 클래스를 상속 받은 클래스이다.
CCmdTarget : MFC의 메시지 맵(윈도우 프로시저 함수의 switch case문을 대체하고자 도입된 구조)과 관련된 코드가 구현된 클래스

┌─────┐
│ CObject   │
└─────┘
          ↑
┌───────┐
│ CCmdTarget  │
└───────┘
         ↑
┌────┐
│ CWnd   │
└────┘

CWnd 클래스
MFC가 제공하는 모든 윈도우 클래스의 기본 기능이 구현된 클래스
MFC가 제공하지 않는 형식의 윈도우를 개발할 때에도 CWnd 클래스가 기본(Base) 클래스가 되어야 한다.

CWnd 클래스는 윈도우 자체를 객체화한 클래스이다. 따라서 CWnd 클래스 객체를 생성하면 화면에 윈도우 하나가 만들어 진다고 할 수 있다.
CWnd m_wndChild;
m_wndChild.Create(TEXT("STATIC"), TEXT("DEMO"), WS_CHILD | WS_VISIBLE | WS_BORDER, CRect(30,30,200,200), this, 1234);

http://msdn.microsoft.com/en-us/library/1xb05f0h%28VS.80%29.aspx
http://msdn.microsoft.com/en-US/library/0yhc9kx4%28v=VS.80%29.aspx

'Win32 API / MFC' 카테고리의 다른 글

TEXT() 매크로  (0) 2010.04.20
Extern "C"  (0) 2009.11.03
# RS232C 포트 즉 직렬(serial) 포트를 통해서 데이터를 전송하는 프로그램  (0) 2009.06.10
헝가리언 표기법  (0) 2009.05.08
코드로 lib 파일 추가하기  (0) 2009.05.08
리눅스 장비에 usb to serial 장치 14개를 붙여서 진행하는 프로젝트가 있었다.
프로젝트 도중 usb serial port가 0~5번까지는 open이 되는데 6번 이상의 port들은 open이 안되는 현상이 계속해서 나타났다.
한참 개고생하다가 지인의 도움으로 해결했다. ㅋ

이럴 땐 "ls -al /dev/ttyUSB*"를 해본다.

#ls -al /dev/ttyUSB*
crw-rw-rw- 1 root root 188,  0 2008-11-14 10:19 ttyUSB0
crw-rw-rw- 1 root root 188,  1 2008-11-14 10:19 ttyUSB1
crw-rw-rw- 1 root root 188,  2 2008-11-14 10:19 ttyUSB2
crw-rw-rw- 1 root root 188,  3 2008-11-14 10:19 ttyUSB3
crw-rw-rw- 1 root root 188,  4 2008-11-14 10:19 ttyUSB4
crw-rw-rw- 1 root root 188,  5 2008-11-14 10:19 ttyUSB5

 디바이스 파일들이 0~5번까지만 생성되어 있기 때문에 open 되지 않았던 것이다.

mknod 유틸을 이용해서 6번부터 13번까지 생성함으로 써 이 문제는 깨끗하게 해결되었다(디바이스 파일은 create()함수를 사용하지 않고 mknod 유틸을 이용해야 한다).

mknod 사용법
mknod [디바이스파일명] [디바이스타입] [주번호] [부번호]

* 여기서 usb to serial 장치는 문자형 장치이기 때문에 디바이스 타입에는 c, 주번호는 188을 사용한다.


mknod /dev/usb-tty/ttyUSB6 c 188 6
mknod /dev/usb-tty/ttyUSB7 c 188 7
mknod /dev/usb-tty/ttyUSB8 c 188 8
mknod /dev/usb-tty/ttyUSB9 c 188 9
mknod /dev/usb-tty/ttyUSB10 c 188 10
mknod /dev/usb-tty/ttyUSB11 c 188 11
mknod /dev/usb-tty/ttyUSB12 c 188 12
mknod /dev/usb-tty/ttyUSB13 c 188 13
mknod /dev/usb-tty/ttyUSB14 c 188 14
mknod /dev/usb-tty/ttyUSB15 c 188 15


3장. 일반적인 개념들

 

3.1. 프로그램이 OS상에서 실행되는 순서 (메모리 탑재, 프로세스 실행)
컴퓨터 운영체제에 프로그램을 탑재하고 실행하면, 다음과 같은 순서로 일이 진행 된다.

1) 사용자는 특정 프로그램을 실행하는 명령어를 입력한다. 혹은 프로그램 아이콘을 클릭한다.
2) 운영체제는 현재 디렉토리에서 프로그램의 파일명을 찾는다. 만약 찾지 못하면 Path로 지정해놓은 프
로그램 목록에서 프로그램의 파일명을 찾는다. 프로그램 목록에서도 못찾으면 운영체제는 에러 메시지를
발생시킨다.
3) 프로그램의 파일명을 찾았다면, 디렉토리로부터 파일의 크기, 하드 디스크내에 프로그램의 물리적인
위치등 파일에 대한 기본적인 정보를 추출한다.
4) 운영체제는 사용 가능한 메모리 공간을 찾아 그 프로그램의 파일을 메모리에 탑재한다. 운영체제는
그 프로그램을 위해 메모리의 특정한 블록을 할당하고 프로그램의 크기나, 위치 등에 대한 정보를
Descriptor Table에 저장시킨다.
5) 운영체제는 중앙처리장치가 해당 프로그램의 첫 기계어를 실행 하도록 분기 명령어를 실행한다. 그
프로그램이 실행되면 그것을 프로세스(Process)라고 부른다. 운영체제는 그 프로세스에게 실행 되는 동
안에는 프로세서ID라는 식별 번호를 부여한다. 이는 프로세스를 추적을 가능하게 한다.
6) 프로세스는 스스로 실행 되며, 그 프로세스를 추적하고, 시스템 자원의 요구(메모리, 디스크 파일,
입출력 장치등)를 받는 것은 운영체제의 몫이다.
7) 해당 프로세스가 종료되면, 핸들은 제거 되고 사용되던 메모리는 다른 프로그램을 위해 해제 된다.

 

3.2. 마지막으로.

 2장에서 공부한 80386에서 현재 나온 최신 CPU인 인텔 듀오2 CPU까지를 통틀어서 모든 32비트 CPU를 IA-32 프로세서라고 한다. 비록 프로세서 성능과 기능면에선 비교할 수 없을 만큼 많은 발전이 있었지만, 이러한 것은 IA-32 표준 뒤에 숨겨져 있다. 프로그래머의 입장에서 보면 IA-32 구조는 80386이후로 실질적으로 바뀐것이 거의 없다. 예외가 있다면 멀티미디어 처리를 위한 고성능 명령어들이 추가 되었다는 것이다. 이런 이유로 80386의 구조는 매우 중요하다. 때문에 80386 프로세서의 내용이 이해가 잘 가지 않는다면 다시 한번 꼼꼼히 참고 하여 보기 바란다. 인터넷에서도 이에 대한 많은 자료를 찾을 수 있고, 친절하게 인텔 메뉴얼 까지 존재한다. (인텔 CPU를 공부 하기 위해서는 이 메뉴얼은 필수 적이다. Intel 홈페이지에서 찾으면 무료로 PDF 파일을 다운로드 받을 수 있다.)

 


'80x86 프로세서' 카테고리의 다른 글

2장. 80386 프로세서 (3/3)  (0) 2010.04.12
2장. 80386 프로세서 (2/3)  (0) 2010.04.12
2장. 80386 프로세서 (1/3)  (0) 2010.04.12
1장. 8086/8088 프로세서 (2/2)  (2) 2010.04.12
1장. 8086/8088 프로세서 (1/2)  (3) 2010.04.12

2장. 80386 프로세서 (3/3) 


2.5. 보호모드

 보호 모드의 특징은 새로운 주소 지정 메커니즘과 보호 수준이다. 새로운 주소 지정 방식에는 세그먼테이션 방식과 페이징이 사용되며, 이는 가상 메모리(virtual memory)지원 하게 된다. 가상 메모리란, 프로세서가 무제한의 물리 메모리를 가지고 있다고 생각하도록 만드는 기술이다. 두 방법 모두 필요에 따라 하드디스크와 사용자 메모리 블록을 교체(swapping)한다.

 보호 모드의 마지막 특징은 개별 프로그램(Task)에 특권 수준(Privilege level)을 부여하는 기능이다. 하위 특권 수준의 프로그램은 상위 특권 수준의 프로그램을 엑세스 할 수 없다. 실제로 운영체제가 가장 높은 특권 수준을, 주로 사용자가 사용하는 응용프로그램에 가장 낮은 특권 수준이 부여 되어 운영체제를 엑세스 할 수 없게 만든다. (물론 게이트란 특별한 형태의 디스크립터로 낮은 특권 수준의 프로그램이 높은 특권 수준의 데이터나 다른 프로그램을 엑세스 할 수 있게 한다.)



2.5.1. 세그먼테이션

 실제 모드와 마찬가지로 보호모드에서도 세그먼트가 존재한다. 하지만 각 세그먼트의 크기는 1바이트에서 4GB(386의 전체 주소 공간 크기)까지 가변적이다. (실제 모드에서의 세그먼트의 크기는 64KB(2의16승)로 고정되어있다.) 그리고 보호모드의 세그먼트 레지스터는 바로 세그먼트의 시작주소를 가리키지 않고  디스크립터 테이블(Descriptor table)을 가리키는 포인터(Pointer)로 사용된다. 386의 메모리 세그먼트는 보호모드에서 동작할 때가 실제 모드에서 동작할 때 보다 유연성이 크다.



보호모드 메모리 세그먼트의 특징

1) 고정된 64KB의 크기 대신 1바이트에서 부터 4GB까지 원하는 크기를 가질 수 있다.

2) 각 메모리 세그먼트에는 보호수준이 부여된다.(하위 보호수준으로 동작하는 프로그램은 상위 보호수준의 세그먼트를 엑세스할 수 없다.)

3) 16,384개의 서로 다른 세그먼트를 정의할 수 있다. (GDT, LDT 포함)

4) 곧바로 디스크로 교체되어 나갈 수 있어, 가상 메모리를 지원한다. (선택된 세그먼트가 메모리에 있는지, 디스크에있는지는 상태 비트를 통해 알 수있다.)

5) 세그먼트는 코드와 데이터 보호를 위해 읽기전용(read-only)로 설정할 수 있다.



용어 정리

1) 셀렉터(Selector)

 보호모드에서는 세그먼트 레지스터가 디스크립터 테이블을 선택하기 때문에 셀렉터라고 부른다.


2) 디스크립터(Descriptor)

 디스크립터의 크기는 8바이트이다. 이 8바이트를 사용하여 해당 세그먼트의 시작주소, 세그먼트의 크기(한계), 세그먼트의 속성들을 설정한다. 하나의 디스크립터당 하나의 물리주소의 세그먼트를 가지고 있다.


3) 디스크립터 테이블(Descript table)

 이런 디스크립터들이 여러개 모인 것을 디스크립터 테이블이라고 한다.(386에는 GDT, LDT, IDT 3종류의 디스크립터 테이블이있다.)


4) 특권 수준(Privilege Level) 

 4단계의 특권 레벨이 존재한다. Level 0이 가장 특권 레벨이 높고, Level 3이 가장 낮다. 레벨의 숫자가 클 수록 특권 수준은 낮다. 특권 수준이 낮으면 높은 특권 수준의 태스크에 접근 할 수 가 없다.



셀렉터와 디스크립터

 보호 모드 메모리 세그먼트를 지정하기 위해서는 세그먼트의 시작주소, 크기, 속성을 알아야 한다. 하지만 16비트 세그먼트 레지스터는 이러한 목적으로 사용하기엔 그 크기가 충분치 않다. 그렇기 때문에 보호모드에서의 세그먼트 레지스터는 디스크립터를 선택하는데 사용된다. 이 선택된 디스크립터 안에 세그먼트의 시작주소, 크기, 속성들이 저장되어 있다.



디스크립터 테이블(Descriptor Tables)
 디스크립터 테이블은 전역 디스크립터 테이블(Global Descriptor Table), 지역 디스크립터 테이블(Local Descriptor Table) 그리고 인터럽트 디스크립터 테이블(Interrupt Descriptor Table)이 존재한다. 모든 디스크립터 테이블들은 가변 길이 메모리 배열이다.(정의된 세그먼트에 따라 테이블의 크기가 가변적이다.) 이 테이블들은 8바이트에서 64KB까지의 크기를 가질 수 있다. 각 테이블은 8,192개의 8바이트 크기를 가진 디스크립터들을 가질 수 있다.



3종류의 디스크립터 테이블

1) 전역 디스크립터 테이블 (GDT, Global Descriptor Table)

 이 디스크립터 테이블의 항목은 시스템의 모든 태스크가 사용할 수 있는 세그먼트들을 기술한다.


2) 지역 디스크립터 테이블 (LDT, Local Descriptor Table) 

 이 디스크립터 테이블의 항목은 주어진 태스크와 관련된 세그먼트를 기술한다. 각 태스크는 별도의 LDT를 가질 수 있다.


3) 인터럽트 디스크립터 테이블 (IDT, Interrupt Descriptor Table)

 이 디스크립터 테이블의 항목은 최고 256개의 서로 다른 인터럽트 서비스 루틴의 시작 주소를 가리킨다.



디스크립터(Descriptor)

 세그먼트의 인덱스가 가리키는 곳을 디스크립터라고 부른다. 디스크립터의 크기는 8바이트이며 이 안에 선형 주소의 블럭에 대한 속성들이 저장되어 있다. 디스크립터는 크게 가리키는 세그먼트의 시작주소(base address), 세그먼트의 크기(한계), 그리고 기타 속성들로 나누워 진다. [그림 2-5-1-1]은 디스크립터의 구성이다.


1) 세그먼트의 시작 주소

Segment Base Address 31~24 비트 (byte 7)

Segment Base Address 23~16 비트 (byte 4)

Segment Base Address 15~ 8 비트 (byte 3)

Segment Base Address   7~ 0 비트 (byte 2)


2) 세그먼트의 크기

Segment Size Limit 19~16 비트(byte 6)

Segment Size Limit 15~8 비트 (byte 1)

Segment Size Limit 7~0 비트(byte 0)


[그림 2-5-1-1] 디스크립터 비트 구성




세그먼트 레지스터(셀렉터)의 구성

 [그림 2-5-1-2]을 참고하면서 설명을 듣자.

세그먼트 레지스터의 2번 비트 가 0일 경우 GDT(Global Descriptor Table)이고, 1일 경우에 LDT(Local Descriptor Table)을 가리킨다. 가리킬 디스크립터 테이블의 인덱스 번호(디스크립터 번호)는 상위 13비트(15~3)를 가지고 결정한다. 총 2의 13(8,192)개의 디스크립터 테이블 인덱스가 존재 한다. 이 상위 13비트로 디스크립터를 선택할 때 디스크립터 테이블의 시작 주소가 저장되어있는 GDTR이나 LDTR과 더한다. (디스크립터 테이블의 시작 주소에 인덱스 번호를 더하면 해당 디스크립터의 시작 주소를 가리킨다. [그림 2-5-1-2] 참고) 마지막으로 하위 2비트(0,1 번째 비트)들은 요청할 특권 수준(RPL, Requestor Privilege Level)을 말한다.


[그림 2-5-1-2] 세그먼트 레지스터 비트 구성

 


세그먼테이션 4단계

1) 세그먼트 레지스터의 두번 째 비트가 0이면 전역 디스크립터 테이블, 1이면 지역 디스크립터 테이블을 가리킨다.


2) 세그먼트 레지스터의 상위 13비트를 시스템 GDTR 또는 LDTR에 더하여 특정 디스크립터를 선택한다. ([그림 2-5-1-2] 참조)


3) 세그먼트 레지스터의 0,1번 비트의 특권 수준이 디스크립터의 특권수준(DPL, [그림 2-5-1-1]의 byte 5에 있는 DPL 참조)과 비교하여 낮으면 Fault(인터럽트)를 일으킨다. (접근할려고 하는 세그먼트 보다 특권 수준이 낮으면 접근 불가)


4) 요청된 특권 수준이 디스크립터의 특권 수준과 같거나 높으면 세그먼트의 32비트 시작 주소([그림 2-5-1-1]의 byte 2, 3, 4, 7 Segment Base Address 참조)에 32비트 offset을 더하여 엑세스할 데이터의 32비트 물리 주소를 얻는다. ([그림 2-5-1-3]  참조)


[그림 2-5-1-3] 세그먼테이션 과정

 



2.5.2. 페이징

 세그먼테이션은 메모리 단편화라는 단점이 있다. 메모리 단편화는 컴퓨터가 가변 길이의 메모리 세그먼트를 관리하려할 때 발생한다. (인터넷에서 메모리 단편화 라고 검색해보자. 자세한 설명이 많이 나온다.) 이 단점을 극복하기 위해 페이징 방식을 도입 하였는데, 이는 가용 메모리 공간을 4KB의 동일한 블럭(페이지)로 나눔으로써 메모리 단편화를 막을 수 있다. 이 페이지는 비교적 크기가 작고 동일한 크기를 가지므로 OS는 좀더 효율적으로 사용 할 수 있다. 고정길이의 페이지가 가변 길이의 세그먼트보다 관리하기가 쉬우므로 OS가 빠르게 반응한다.

 페이징 방식은 제어레지스터 CR0의 31번째 비트를 1로 셋 시키면 enable 되며, 32비트의 선형 주소를 별도의 페이지 디렉토리 표(Page Directory Table)와 페이지 변환표(Page Translation Table 또는 Page Table)를 통하여 4KB 페이지 프레임 내의 새로운 물리주소를 계산하게 한다. ([그림 2-5-2-1]을 참고하자.)



주소변환의 3단계 

[그림 2-5-2-1]을 참고 하면서 읽어 나가자.

1) 선형 주소의 상위 10비트(Dir)을 오프셋으로 하여, CR3 레지스터(페이지 디렉토리의 시작주소를 가지고 있다.)의 주소와 더해져 해당 페이지 디렉토리의 항목을 정한다. 해당 페이지 디렉토리 항목엔 페이지 변환표의 시작 주소가 들어있다. (페이지 디렉토리 각 항목은 해당 페이지 변환표를 가리키고 있다.)


2) 선형 주소의 중간 10비트(Table)는 Dir에서 지정된 페이지 디렉토리의 항목과 더해져 해당 페이지 변환표의 항목을 정한다. 이 항목엔 물리 메모리에서 나누워진 어떤 4KB 블럭의 시작 주소를 가지고 있다.


3) 페이지 변환표에서 얻은 4KB의 시작 주소에 선형 주소의 Offset 부분을 더해 물리 주소를 구하게 된다.


[그림 2-5-2-1] 페이징 

 



2.5.3. 세그먼테이션과 페이징의 혼합

 세그먼테이션방식과 페이징의 혼합된 방식이다. 실제 이 방식으로 구현이 되어있으며, 페이징 기능을 사용하지 않을 때(CR0 레지스터의 31번째 비트가 0일 경우)는 세그먼테이션으로 나온 프로세서의 선형 공간이 프로세서의 물리 주소 공간으로 바로 매핑(mapping)된다. 페이징 기능을 사용할 경우엔 세그먼테이션으로 얻어진 선형 주소가 페이징 방식에 필요한 32비트 선형 주소가 된다. 그 이후 변환과정은 앞에서 설명한 페이징 방식과 동일하다.


[그림 2-5-2-2] 세그먼테이션 과 페이징




2.5.4. 특권 규칙 

 멀티 태스킹 OS에서는 실행되는 프로그램은 절대로 특권이 높은 데이터나 프로그램(태스크, Task)을 엑세스해서는 안된다. 그렇지 않으면 운영체제를 포함한 다름 모든 태스크들을 다운시킬 수 있다. 386은 3가지 특권 수준(PL : Privilege Level)을 제공하는데 0(2진수 00)에서 3(2진수 11)까지 있다. 낮은 특권 수준은 주로 사용자의 응용 프로그램에 부여되며, 높은 특권 수준은 OS의 커널에 부여된다. 사용되는 경우는 세그먼테이션 4단계에서 설명 했다.

'80x86 프로세서' 카테고리의 다른 글

3장. 일반적인 개념들  (0) 2010.04.12
2장. 80386 프로세서 (2/3)  (0) 2010.04.12
2장. 80386 프로세서 (1/3)  (0) 2010.04.12
1장. 8086/8088 프로세서 (2/2)  (2) 2010.04.12
1장. 8086/8088 프로세서 (1/2)  (3) 2010.04.12

2장. 80386 프로세서 (2/3) 

2.4. 레지스터

 1장에서 말했듯이 레지스터란 중앙처리장치 내부에 있는 고속의 저장장치로서 메모리보다 빠른 엑세스를 위해 설계되었다. 80386의 레지스터는 8개의 범용 레지스터, 6개의 세그먼트 레지스터(8086에서난 4개의 세그먼트레지스터가 있다.), 그리고 상태 플래그와 명령어 포인터를 가지고 있다. 이 레지스터들은 이전 CPU(8086, 80286등..)들의 레지스터들을 다 포함 한다.(하위 호환성 유지)

 

[그림 2-4-1] 범용 레지스터, 세그먼트 레지스터, 명령어 포인터, 상태 플래그 레지스터

 

 

범용 레지스터

 범용 레지스터는 계산과 데이터 이동에 주로 사용된다. 이 레지스터들은 [그림 2-4-2]에서 보는 것처럼 하나의 32비트 값 혹은 16비트, 8비트 값으로 처리 될 수 있다.

예를들어 범용 레지스터인 EAX는 32비트 레지스터 이고, AX는 16비트, AH(상위비트),AL(하위비트) 은 8비트 레지스터이다.

 

[그림 2-4-2] 32비트, 16비트, 8비트 범용레지스터, 32비트 명령어 레지스터, 16비트 명령어 레지스터

 

[표 2-4-1] 32,16,8비트로 사용할 수있는 레지스터

32비트

16비트

8비트(상위)

8비트(하위)

EAX AX AH AL
EBX BX BH BL
ECX CX CH CL
EDX DX DH DL
EAX : 곱셈과 나누셈 명령에서 자동으로 사용된다. 확장된 누산기(EAX, extended accumulator)레지스터 라고 부른다.
ECX : 루프 카운터로 사용된다.
 

[표 2-4-2] 32비트, 16비트 인덱스,포인터 레지스터

32비트

16비트

ESI SI
EDI DI
EBP BP
ESP SP
ESI(Extended Source Index) : 고속 메모리 전송 명령에 사용된다.
EDI(Extended Destination Index) : 고속 메모리 전송 명령에 사용된다.
EBP(Extended Base Pointer) : 고급언어에서 스택 상에 있는 지역 변수와 함수 매개변수를 참조하기 위해 사용된다. 일반적인 계산이나 데이터 이동을 위해 사용해서는 안된다.
ESP(Extended Stack Pointer) : 스택에 있는 데이터를 가리킨다. 이 레지스터는 일반 적인 계산이나 데이터 이동을 위해 절대로 사용 될 수 없다.
[표 2-4-2]에서의 16비트 레지스터들은 80386의 실제모드(real mode)에서 수행되는 프로그램 작성시에만 사용된다.
 
 
명령어 레지스터(IP, Instruction Point)
명령어 포인터(IP)의 32비트 레지스터 이름은 EIP이다. 명령어 포인터는 바로 다음에 실행할 명령어 주소의 오프셋이 들어 있다. 이 오프셋(EIP)은 항상 코드 세그먼트(CS)와 결합된다. EIP의 하위 16비트는 IP이다. 이 16비트 레지스터는 실제 모드에서 사용된다.
 
[표 2-4-3] 32비트, 16비트 명령어 포인터 레지스터

32비트

16비트

EIP IP
 
 
세그먼트 레지스터
 80386의 세그먼트 레지스터는 실제모드에서 8086과 동일한 기능을 한다. 하지만 보호모드에서는 새로운 주소 지정방식이 사용된다. 세그먼트 레지스터가 여전히 유지 되지만, 각 세그먼트의 크기는 1바이트에서 4GB까지의 크기를 가질 수 있다. 이 때 세그먼트 레지스터에 저장된 주소는 [그림 2-4-3]처럼 디스크립터 테이블(descriptor table)을 가리키는 포인터로 해석된다. 자세한건 보호모드에서 알아 보도록 하자.
 
[그림 2-4-3] 디스크립터 레지스터를 선택하고 있는 세그먼트 레지스터
 
플래그 레지스터
 플래그 레지스터도 80386으로 넘어오면서 32비트로 확장 되었다. 8086의 상태 및 제어 플래그가 그대로 유지 되었지만, [그림 2-4-4]에서 보는 것 처럼 4개의 플래그가 새롭게 추가 되었다.
VM(Virtual 8086 Mode) : 가상모드. 이 플래그는 프로세서를 가상 8086모드로 전환하는데 사용되는 보호 모드 제어 플래그이다.
RF(Resume Flag) : 재개 프래그. 디버그 레지스터와 함께 사용 된다. set되면 디버그 고장은 무시되고 다음 명령어가 정상적으로 사용된다.
NT(Nested Task Flag) : 내포 태스크. 보호 모드에서 현재 태스크가 다른 태스크에 의해 호출되었음을 나타내는 데 사용된다. 이는 내포된 태스크가 끝났을 때 실행될 반환(return) 명령어의 형태에 영향을 미친다.
IOPL(Input/Output Privilege Level) : 입출력 특권 수준. 이 두 개의 보호모드 제어 비트는 I/O명령어를 실행하는 데 필요한 현재 특권수준(0-3)을 나타낸다. 이에 따라 운영체제는 태스크의 I/O특권을 제어한다.
 
[그림 2-4-4] 플래그 레지스터
 
 
제어 레지스터
 이 레지스터들은 보호 모드에서 프로세서 제어와 검사를 위한 목적을 가지고 있으므로 정상적으로는 응용 프로그래머는 사용하지 않는다.
 
CR0 : 페이징 메커니즘의 활성화, 태스크 전환의 감시, 보조프로세서 에뮬레이션의 인에이블, 보호 모드와 실제 모드 동작의 선택에 사용된다.
CR2 : Page fault를 일으킨 마지막 명령어의 주소를 가지고 있다. Page fault란 메모리에 있지 않은 페이지나 세그먼트에 대한 참조를 말한다. page fault가 일어나면 해당 페이지를 디스크에서 가져와 메모리에 적재 하여야한다.
CR3 : 페이징을 통한 가상 메모리가 인에이블 되었을 때 사용된다. 이 레지스터는 페이지 디렉토리의 시작 주소를 가지고 있다. 이 항목은 페이지 변환 표라고 하는 표에 들어있는 항목의 위치를 찾는 데 사용된다. 페이지 변환 표란 4KB 크기의 페이지 프레임의 물리적 시작 주소와 그 프레임에 대한 엑세스 정보를 가지고 있는 표이다.
 
[그림 2-4-5] CR0 레지스터

 

[그림 2-4-6] CR2, CR3 레지스터

 

시스템 주소 레지스터

 보호 모드에서 사용되는 디스크립터 테이블에 대한 정보를 저장하기 위해 제공되는 레지스터이다. (GDTR, ITDR, TR, LDTR -> 4개가 제공된다.) 자세한건 보호모드에서 알아 보도록 하자.

 

[그림 2-4-7] 시스템 주소 레지스터


'80x86 프로세서' 카테고리의 다른 글

3장. 일반적인 개념들  (0) 2010.04.12
2장. 80386 프로세서 (3/3)  (0) 2010.04.12
2장. 80386 프로세서 (1/3)  (0) 2010.04.12
1장. 8086/8088 프로세서 (2/2)  (2) 2010.04.12
1장. 8086/8088 프로세서 (1/2)  (3) 2010.04.12

2장. 80386 프로세서 (1/3) 

 

2.1. 개요

 8086/88의 후속작은 보호모드를 최초로 지원하는 CPU 80286이다. 이때 당시 MS-DOS가 주로 사용되었기 때문에 80286에서 보호모드를 사용하는 경우는 거의 없었다. 80286은 8086과 같이 16비트 CPU이다. 보호모드를 지원하는 것과 주소 버스가 24비트(16MB 메모리 지원)인 것을 빼면 8086과 다를 빠 없었다. (속도가 빠른 8086 이라고 보면 된다.) 그래서 80286은 그냥 이 정도 설명에서 넘어가도록 하겠다.

 

 80386(Intel386 DX)은 싱글유저 응용프로그램과 MS-DOS나 Windows같은 운영체제를 위해 디자인된 32비트 프로세서이다. 32비트 레지스터들과 32비트의 데이터버스, 주소버스를 가지고 있다.

이 프로세서는 4기가의 물리적 메모리(2의 32승)와 64테라바이트(2의 48승)의 가상 메모리를 지원한다. 80386이 중요한 이유는 이후 등장하는 모든 32비트 CPU가 80386을 근간으로 개발되었기 때문이다. 이를 IA-32 프로세서라고 한다. 때문에 80386은 모든 8086 family(8086, 8088, 80186, 80188, 80286)들과 하위 호환성을 지원한다. 또한 80386은 실제모드, 보호모드, 가상 8086모드 의 3가지 동작 모드를 지원한다. 여러모로 8086이나 80286의 내부구조에 비해 많은 부분이 변하였다.

 

 

[표 2-1-1] 참고

CPU 출시년도 트랜지스터수 제조 공정 패키지 최대 클럭 외부 데이터 버스 레지스터 주소 버스 L1 Cache L2 Cache
80286 1982 134,000 1.0 microns 68 pin PLCC or PGA 12.5 MHz 16 16 24 none none
80386 1985 275,000 1.0 microns 132 pin PGA or QFP 33 MHz 32 32 32 none external

 

2.2. 기본 구조 (Base Architecture)

 80386은 중앙 처리 장치(CPU, a central processing unit)과, 메모리 관리 장치(MMU, a memory management unit), 그리고 버스 인터페이스 장치(BIU, Bus Interface Unit)로 구성된다.

 

CPU(Central Processing Unit) 중앙처리장치는 실행장치(EU, execution unit)와 명령어 장치(instruction unit)로 구성된다. 실행장치(EU)는 ALU(arithmetic logic unit)와 8개의 32비트 범용 레지스트를 가지고 있다. (8086의 레지스터는 16비트) 80386도 8086처럼 명령어의 인출과 실행을 겹치도록하여(파이프라인 구조), 시스템의 성능을 최적화 시킨다.

 

MMU(Memory Management Unit) 메모리 관리 장치는 세그멘테이션 장치와 페이징 장치로 구성된다. 자세한 내용은 세그먼테이션 기법, 페이징기법에서 다룬다.

 

BIU(Bus Interface Unit) 이 장치는 여러 제어 신호와 함께, 386의 32비트 주소 버스와 데이터 버스를 관리한다. 8086의 BIU처럼 프로세서가 명령어 인출을 기다리지 않도록 명령어 큐를 가득채우는 일을 한다.(80386에서는 명령어 큐 16바이트로 확장)

 

[그림 2-2-1] 80386의 기본 구조

 

  

2.3. 동작모드 

 

2.3.1. 실제모드 (real mode)

 CPU에 처음 전원이 들어오면 80386은 실제 모드에서 시작된다. 이 모드의 80386은 8086과 기능이 완전히 동일하다.

주소 선은 20개의 하위 비트 A0-A19만 사용 되서 주소 공간이 1MB로 제한된다. 상위 주소선 A20-A31은 비활성화 된다. 그리고 8086의 세그먼티드 메모리 주소 지정 방식이 사용되며, 각 세그먼트의 크기는 64K로 제한된다. 또한 프로그래머는 80386의 32비트 레지스터를 사용할 수 있다.

 

2.3.2. 보호모드 (protected mode)

 80386의 강력하고, 고유한 기능을 사요하기 위해서는 보호모드에서 작동 되어야 한다. 보호모드에서는 가상메모리(세그먼테이션과 페이징 기법)을 지원하고, 개별 테스크에 특권 수준을 부여 하는 기능을 제공한다. 하위 특권 수준의 테스크는 상위 특권 수준을 가지고 있는 세그먼트의 프로그램이나 데이터를 엑세스 할 수 없다. 이 방식으로 운영체제는 각각으로부터 자신이 보호되도록 여러 개의 프로그램을 수행 시킬 수 있다. 자세한 부분은 보호 모드에서 알아 보도록 하자.

 

2.3.3. 가상 8086 모드(virtual 8086 mode)

 이 모드에서는 80386은 각각의 실제 모드 프로그램에 자신의 1MB 메모리 블록을 할당한다. 이러한 방식으로 여러 개의 8086/88 프로그램을 각각으로부터 보호하면서 동시에 실행할 수 있다. 동시에 실행시킬 수 있는 프로그램의 수는 제한이 없다. 가상 386모드는 보호 모드의 특징이다. (동시에 보호모드와 가상 8086모드를 동작 시킬 수 있다.) 각 8086테스크에는 가장 낮은 특권 수준이 부여되므로 다른 세그먼트에 있는 프로그램이나 데이터는 엑세스할 수 없으며, 따라서 각 테스크가 보호된다.

 

'80x86 프로세서' 카테고리의 다른 글

3장. 일반적인 개념들  (0) 2010.04.12
2장. 80386 프로세서 (3/3)  (0) 2010.04.12
2장. 80386 프로세서 (2/3)  (0) 2010.04.12
1장. 8086/8088 프로세서 (2/2)  (2) 2010.04.12
1장. 8086/8088 프로세서 (1/2)  (3) 2010.04.12

1장. 8086/8088 프로세서 (2/2)

  

상태플래그와 제어 플래그

 

[그림  1-5-2] 제어 레지스터 (상태플래그, 제어플래그)

  

플래그

설명

1 일때

0 일때

OF(overflow) 자리 넘침 OV(overflow) NV(not overflow)
DF(direction) 방향 DN(down) UP(up)
IF(interrupt) 가로채기 EI(enable) DI(disable)
SF(sign) 부호 NG(negative) PL(plus)
ZF(zero) 영(0) ZR(zero) NZ(not zero)
AF(aux,carry) 하위 4bit 캐리 AC(auc,carry) NA(not aux)
PF(parity) 패리티 PE(parity even) PO(parity odd)
CF(carry) 자리 올림 CY(carry) NC(not carry)

 

CF(Carry Flag)
 연산 명령을 실행한 후에 최상위 비트에서 덧셈에 의한 자리 올림(carry)이나 뺄셈에 의한 자리 내림(borrow)이 있을 경우 Set(해당 bit가 1이 되면 set, 0이 되면 reset)된다. 바이트 단위 연산일 때는 D7비트, 워드 단위일 때는 D15 비트가 대상이 된다. 논리 연산 명령에서는 0으로 reset된다. 로테이토, 쉬프트 명령에서는 해당 데이터의 최상위 또는 최하위 비트가 CF로 전송된다.


MSB (Most Significant Bit) : 최상위 비트
LSB (Least Signficant Bit) : 최하위 비트

 

PF(Parity Flag)

 데이터 전송 등에 따른 결과가 짝수 패리티인 경우에 set되고, 홀수 패리티일 때 reset된다. 이 플래그는 주로 데이터 전송시 에러가 발생 했는지 발생하지 않았는지 조사할 때 쓰인다. 하드웨어가 처리하는 부분이므로 프로그래머 입장에서는 신경쓰지 않아도 된다.


AF(Auxiliary Flag)

 산술 연산 도중에 하위 4비트에서 상위 4비트로 자리 올림이 생기거나, 또는 상위 4비트에서 하위 4비트로 자리 내림이 있을 때 1로 set된다. 이 플래그는 10진 연산의 경우 보정하는데 사용된다.


ZF(Zero Flag)

 각 연산의 결과가 0이 될 경우 set된다. 비교 명령을 실행하면 비록 레지스터 내용은 변하지 않지만 실행 결과에 따라서 set될 수 있다.


SF(Sign Flag)

 연산 결과 최상위 비트가 1이 되면 set된다. SF는 연산 후 그 결과 값의 부호를 나타내는데 사용하며 최상위 비트가 0일 경우 양수, 1일 경우엔 음수가 된다.

 

OF(Over Flow Flag)

 연산결과 오버플로우가 발생했을때 set 된다. 오버플로우가 생기면 원하는 데이터가 망가져서 원하는 데이터를 얻을 수 없으며 프로그램엔 치명적인 에러를 방생한다.0으로 나누었을 때 발생하는 오버플로우에 대해서는 CPU에 의해서 내부적으로 오버플로우 인터럽트가 발생하고, 프로그램은 보통 정지하게 된다.


IF(Interrupt Enable Flag)

 하드웨어에 의한 인터럽트를 받아들일 것인가, 받아들이지 않을 것인가를 나타낸다. 1로 set되어 있을 경우 인터럽트를 받아들이고, 0으로 reset되어 있을 경우엔 받아들이지 않는다. 단 NMI(Non-Maskable Interrupt)는 이 플래그의 값에 관계없이 받아들인다.

 

DF(Direction Flag)

 문자열에 관한 명령을 실행할 때, 이 비트에 따라서 소스 또는 데스티네이션 어드레스를 자동적으로 하나씩 증가 또는 감소 시킨다. 0일 때 어드레스가 자동적으로 증가하고, 1일 경우 어드레스가 감소한다.

 

TF (Trap Flag)

 명령 실행 후에 CPU는 이 플래그를 조사하여 1이면 싱글 스텝 인터럽트를 발생한다. 이플래그를 1로 해두면 CPU는 하번에 1개의 명령만 실행한다. 이 기능을 이용하여 디버깅 프로그램을 만들 수 있다.

 

 

1.6. 세그먼티드 메모리

 

1.6.1. 메모리 맵 

 8086/88의 메모리 공간은 64KB 블록 16개로 분할되어 있다. 16진수 00000h 에서 FFFFFh로 끝나는 메모리 주소를 가지고 있다. 64K의 블록으로 분할되어 있기 때문에 16진으로 64K만큼 하나만 증가 시켜 버리면 블록이 바뀌기 때문에 편리하다. (메모리 주소에서 20000h 는 10000h 보다 65,536바이트/64K 높은 위치에있다.)

 

 [그림 1-6-1]에서 보는 것과 같이 메모리 주소가 일직선으로 연속된 공간이라고 생각하고, 시스템 메모리가 어떻게 할당 되어 있는가를 보이고있는 것을 메모리 맵(memory map)이라고 한다. 예를 들면 RAM영역은 00000h 에서 9FFFFh까지 할당되었고, Video Display RAM 영역은 A0000h에서 BFFFFh 까지 할당, ROM영역은 C0000h에서 FFFFFh까지 할당된다. 프로그래머는 이를 확실하게 알아야 정확히 메모리의 어느 부분에 안전하게 데이터를 적재할 수 있다.

 

[그림 1-6-1] 8086/88의 메모리 맵

 

 

 아래의 [그림 1-6-2]는 MSDOS의 메모리 맵이다. 도스는 8086 CPU에서 설계 되었다. 따라서 메모리의 크기가 1MB로 한정되었다. 호환성의 이유로 1MB의 주소 공간을 아래의 메모리 공간처럼 블록으로 분할 하였다. (메모리의 1MB는 640K의 사용자 메모리와 384K의 시스템 메모리로 구성)

도스 시절부터 컴퓨터를 사용했다면 아마, 게임을 하기위에 640K 의 메모리를 최대한 활용할려고 애를써본 기억이 있을 것이다. 이때의 메모리가 도스의 유저메모리 공간이다.

 

[그림 1-6-2] MSDOS 의 메모리 맵

 

 

 

1.6.2. 세그먼트 레지스터, 오프셋 레지스터(포인터, 인덱스 레지스터)

 1.5. 레지스터의 세그먼트 레지스터를 다시 한번 살펴보자. 64K로 나눈 공간을 세그먼트라고 하였다. 그 세그먼트를 저장하는 레지스터가 세그먼트 레지스터이다. 8086/88의 세그먼트 레지스터는 총 4가지가 있다. (코드 세그먼트(CS), 데이터 세그먼트(DS), 스택 세그먼트(SS), 엑스트라 세그먼트(ES) - [그림 1-5-1] 8086 레지스터의 구성 참고)

여기서 코드 세그먼트는 프로그램 명령어가 저장된 세그먼트 영역의 시작주소를 저장하고, 데이터 세그먼트는 프로그램에 사용되는 데이터가 저장된 세그먼트의 첫 주소를 저장한다. 엑스트라 세그먼트 또한 데이터 세그먼트와 같다.(대개 공유 데이터를 저장하는데 사용된다.) 그리고 스택 세그먼트는 인터럽트와 서브루틴의 반환 주소를 저장하는데 사용된다. (스택에 대해서는 2부 어셈블리 에서 자세하게 소개하겠다.) 또 4개의 세그먼트가 반드시 분리 되서 정의될 필요는 없다. [그림 1-6-3]을 보면 SS영역과 ES이 서로 겹쳐 있는 걸 알 수 있다. 실제로 4개의 세그먼트가 완전히 같은 경우도 허용된다. (CS=DS=ES=SS) 

 

[그림 1-6-3] 각 세그먼트의 시작 주소가 세그먼트 레지스터에 저장되어 있는 것을 표현한 것이다.  

 

 세그먼트 레지스터의 값은 64K로 나눈 세그먼트 블록의 첫번 째 주소(base address)이기 때문에, 각 세그먼트 블록 안의 메모리 영역에 접근하기 위해서는 오프셋 레지스터(포인트, 인덱스 레지스터)가 필요하다. 1.5. 레지스터의 포인터 레지스터와 인덱스 레지스터를 다시 자세히 알아보자.

 

[표 1-6-1] 오프셋 레지스터 - SI, DI, IP, SP, BP

SI(Source Index      )

DI(Destination Index)

IP(Instruction Index )

SP(Stack Pointer      )

BP(Base Pointer       )

 

 다시 한번 강조하지만 세그먼트 레지스터로는 64KB 크기의 세그먼트 첫 번째 주소밖에 지정하지 못한다. 64KB내에서 원하는 임의의 주소를 지정하기 위해서 16비트 크기의 레지스터가 하나 더 필요한데 이때 사용하는 레지스터가 오프셋 레지스터이다.

 

SI(Source Index), DI(Destination Index)
 문자열을 다루는 명령에서 소스 데이터의 오프셋 어드레스를 가리킬 때는 SI를 사용하고, 데스티네이션 어드레스를 가리킬 때 DI를 사용한다.
 
IP(Instruction Pointer)
 명령코드가 들어있는 세그먼트의 오프셋 어드레스를 지정하는데 사용한다. 이때의 세그먼트를 지정하기 위해서는 반드시 CS를 사용해야 한다. 이 포인터는 프로그래머는 사용할 수없다.

SP(Stack Pointer)
 스택 세그먼트의 오프셋 어드레스를 지정하는데  사용된다. 스택 세그먼트를 지정하는 세그먼트 레지스터로는 SS만을 사용해야 한다. 하지만 스택내의 오프셋을 나타내는데는 SP외에 BP로도 사용 할 수 있다.
 
BP(Base Pointer)
 SP와 마찬가지로 스택의 오프셋을 가리키는데 사용한다. SP와 다른 점은 PUSH와 POP명령에 의해 자동적으로 변하지 않는다는 것이다. 전달받은 인수를 함수 내부에서 가리킬 때 주로 사용한다.

 

1.6.3. 세그먼트 메모리 기법 

 세그먼트 내에서 주소는 0에서부터 시작하여 FFFF까지 이다.(64K의 길이, 오프셋 레지스터의크기는 16비트이기 때문이다.) 세그먼트 내에서의 주소는 오프셋(offset) 또는 논리 주소(logical address)라고 한다. 그럼 물리 주소(physical memory)는 무엇인가? 바로 메모리의 실제 주소를 뜻한다.

 세그먼트 레지스터는 16비트이기 때문에 실제 메모리 주소(20비트)에 분할된 세그먼트 블록의 첫 주소를 저장하지 못한다. 해결 방법은 실제주소의 하위 비트를 4개를 생략하고 저장을 한다. 반대로 세그먼트 레지스터의 값을 실제 주소로 바꿀 땐 하위비트 뒤에 0000을 추가한다. (이는 레지스터의 내용에 16을 곱한것이다.) 예를 들어 [그림 1-6-4]를 보자. 그림에서 색칠되어 있는 부분을 코드 세그먼트(CS)라고 가정하자. 코드 세그먼트의 논리 주소(오프셋)을 0250h 라면(CS : 8000, Offset : 0250) , 실제 주소(물리주소)는 80000 + 0250으로 80250h 이다.

 

   80000  ( CS의 8000h 의 하위비트에 0 추가 ) -> 16진수이기 때문에 0을 한개 붙였다. 2진수일경우 0 4개를 추가한다.

+)_0250  ( CS의 오프셋 )

--------- 

   80250  (실제 물리 주소)

 

세그먼트 레지스터와 오프셋 레지스터, 이 두개의 16비트 레지스터를 이용해서 20비트의 메모리에 접근 하는 방법을 세그먼트 메모리 기법이라고 한다.

 

물리 주소 : 20비트의 길이를 가지고 있고, BIU가 주소 버스 선에 내보내는 실제의 이진 코드

논리 주소 : 주어진 세그먼트의 0위치로 부터의 오프셋

  

[그림 1-6-4] 세그먼트화된 메모리맵, 실제 주소 모드

 

 

 두 세그먼트가 겹치는 경우가 있다고 했다. 심지어 4개의 세그먼트까지 중복으로 사용 가능하다. 여기서 발생하는 문제가 있는데, 바로 세그먼트와 오프셋 조합이 중복되는 경우이다. 이는 물리 주소가 중복된다는 말과 동일하다.  이 때 데이터가 서브루틴 스택에 덧쓰기를 하거나 반대로 스택에 저장되는 주소가 데이터를 덧쓰게 되면 큰 문제가 발생한다. 그렇기 때문에 세그먼트가 겹칠때에는 각별히 주의해야한다.

 

물리 주소가 겹치는 예

ES : 52B9h, offset : D470h -> 52B90 + D470 = 60000h

SS : 5D27h, offset : 2D90h -> 5D270 + 2D90 = 60000h

 

마지막으로 세그먼트와 오프셋의 표기법을 알아보자.

스택 세그먼트의 논리 주소 2D90h를 표현 할려면 SS:2D90h 라고 쓴다. 이렇게 표현하면 물리 주소는 같더라도 프로그래머가 알아보기가 명확해진다.

 

각 세그먼트별로 사용해야하는 오프셋 레지스터는 2부 어셈블리에서 자세하게 배운다.

'80x86 프로세서' 카테고리의 다른 글

3장. 일반적인 개념들  (0) 2010.04.12
2장. 80386 프로세서 (3/3)  (0) 2010.04.12
2장. 80386 프로세서 (2/3)  (0) 2010.04.12
2장. 80386 프로세서 (1/3)  (0) 2010.04.12
1장. 8086/8088 프로세서 (1/2)  (3) 2010.04.12

1장. 8086/8088 프로세서 (1/2)

 

 

1.1. 개요

 16비트 프로서세인 8086 마이크로프로세서(이하 8086)는 1970년대 후반에 등장하였다. 16비트 명령어가 도입 되었고, 하드웨어에 의한 곱셈과 나눗셈을 수행할수 있었다. 그리고 20비트의 주소 버스를 사용하여 1MB까지의 메모리를 엑세스 할 수 있었다. 이후 등장하는 80x86 마이크로프로세서(이하 80x86)들은 8086을 기초로 만들어 지고, 발전 됐다. 이 말은 곧 하위 호환성을 가진다는 말이 될 것이다. 실제로 8086용으로 제작된 프로그램이 지금 CPU에서도 잘 작동 된다. 따라서 8086을 잘 이해한다면 상위 CPU모델들을 이해하는데 큰 도움이 될 것이다.

 

 

 

[표 1-1-1] 참고

CPU 출시년도 트랜지스터수 제조 공정 패키지 최대 클럭 외부 데이터 버스 레지스터 주소 버스 L1 Cache L2 Cache
8086 1978 29,000 3.0 microns 40 pin DIP 10 MHz 16 16 20 none none
8088 1979 29,000 3.0 microns 40 pin DIP 10 MHz 8 16 20 none none
 
 

1.2. 8086의 구조

 8086은 버스 접속 장치(BIU, bus interface unit)와 실행 장치(EU, execution unit)로 구성된다. 여기서 버스 접속 장치(이하 BIU)와 실행 장치(이하  EU)를 알아 보자.

 

[그림 1-2-1] 참고

 

 

BIU : 프로세서와 외부 장치와의 데이터 전달에 필요한 메모리주소나 I/O주소의 생성을 담당하는 하드웨어 기능 제공

EU : BIU로 부터 프로그램 명령어 코드와 데이터를 받아들여, 명령어를 수행한 다음, 범용 레지스터에 결과를 저장하는 기능 제공. EU는 BIU를 통해서 모든 데이터를 받고 보낸다.

 

 

1.3. 인출(fetch) 사이클과 실행(excute) 사이클

 

인출(fetch) : IP(Instruction pointer) 레지스터가 가리키고있는 주소의 명령어를 가져 오는 것.

실행(excute) : 인출한 명령어를 실행 하는것.

 

 8086은 동작 속도를 높이기 위해서 앞에서 설명한 BIU와 EU로 구성 하였다. 이는 인출 사이클과 실행 사이클이 중첩되게 할 수 있다. 이를 알아 보기 위해 8086이 처음 시작할 때 하는 행동을 살펴보자.

 

① BIU가 명령어 포인터 레지스터의 내용을 주소 버스로 보내어 메모리의 선택된 바이트 혹은 워드가 BIU로 읽혀 들어오게 한다.

② IP 레지스터를 하나 증가 시켜 다음 명령어 인출을 준비한다. (크기에 따라 둘 이상 증가 되기도 한다.)

③ BIU에 들어온 명령어는 큐(queue)에 저장된다. 큐는 선입출(FIFO)방식인 저장 레지스터이다.

④ 제일 초기엔 큐가 비어 있기 때문에, EU는 바로 큐에서 명령어를 꺼내어 실행한다.

⑤ EU가 가지고온 명령어를 실행하고 있는 동안, BIU는 새로운 명령어 인출을 시작한다. 첫번째 명령어의 실행 시간에 따라 다르지만, EU가 다음 명령어를 큐에서 꺼낼 준비가 될 때 까지는 BIU는 명령어 큐에 여러 개의 명령어를 저장 할 수 있다.

⑥ BIU는 큐에 명령어를 채우고, EU는 이 명령어를 인출하고 실행하는 사이클이 계속 된다.

 

 BIU는 명령어 큐에 두 바이트 이상 저장 공간이 생길 때 마다 새 명령어를 인출 하는데, 이러한 파이프 구조는 BIU가 새 명령어를 인출 할 때 까지 기다리지 않고, EU가 거의 연속적으로 명령어를 실행 할 수 있게 한다. 이는 CPU의 동작 속도를 크게 향상 시킨다.

 

 하지만 EU가 대기 모드에 들어가는 경우가 있는데, 3가지 조건이 있다. 첫번 째 조건은 명령어가 큐에 있지 않는 메모리 위치를 엑세스 할 필요가 있을 때 일어난다. BIU는 명령어 인출을 보류하고 이 메모리 위치의 주소를 출력한다. 메모리 엑세스를 기다린 후에 EU는 큐로 부터 명령어를 꺼내어 실행을 재개 하고, BIU는 계속해서 명령어 큐를 채운다. 두 번째 조건은 실행 될 명령어가 점프 명령어일 때 일어난다. 이 경우, 제어는 새로운 주소로 전달(비순차적이다) 되어야 하지만 큐는 명령어가 항상 순차적으로 실행된다고 가정하고 틀린 명령어 코드를 저장하고있다. EU는 점프 주소에 있는 명령어가 인출되는 동안 기다려야 한다. 현재 큐에 들어가 있는 모든 명령어는 버려진다.(덮어쓰기가 이루어짐) 마지막 세번 째 조건은 BIU가 명령어 인출을 멈추게 하는 경우이다. 이는 실행속도가 느린 명령어를 실행할 때 일어난다. 이런 명령어들은 하나만 실행 해도 명령어 큐가 다 차 버린다. 따라서 BIU는 EU가 큐에서 하나 또는 두 바이트를 꺼내 갈때 까지 기다린 후에 다시 인출을 진행한다.

 

[그림 1-3-1] 인출과 실행 사이클, 명령어 파이프 라인

 

 

1.4. 8088 프로세서란? 

 위의 [표 1-1-1 ] 참고를 보면 알겠지만, 기본적인 구조는 8086과 동일하다. 유일한 차이점은 BIU이다. 8086은 16비트 버스이지만, 8088은 그 반인 8비트 버스이다. 명령어 큐 사이즈도 작아졌다.(8086 명령어 큐 사이즈 : 6바이트, 8088 명령어 큐 사이즈 4바이트) 지금으로 치자면 팬티엄의 보급형으로 나온 셀러론급 CPU라고 생각해도 무방하다. EU는 동일하기 때문에 프로그래머 입장에서는 프로그래밍하는 것이 동일하다. 그러므로 8086 구조만 알면 된다. (8088용 프로그램은 변경없이 8086에서 실행 가능하다.)

 

 

1.5. 레지스터

 레지스터란 CPU가 여러 가지 명령을 실행할 때, 데이터나 계산의 중간 결과를 일시적으로 보관하거나, 각종 연산의 처리, 주소 지정등에 사용되는 CPU내부의 램(RAM)을 말한다. 하드웨어 적으로 외부 메모리인 램(RAM)이나 롬(ROM)과 달리 CPU안에 들어 있으며, 버스 인터페이스의 내부 버스에 직접 연결되어 있기 때문에 외부 메모리에 비해서 CPU의 엑세스 시간이 훨씬 짧고 지정 방법도 간단하다.

 

[그림 1-5-1] 8086 레지스터의 구성

 

범용 레지스터(General Registers)

 데이터 레지스터, 데이터 그룹이라고도 불리며, 누산기(AX 레지스터, Accumulation)와  BX, CX, DX 레지스터로 구성된다. 각 레지스터의 크기는 16비트지만, 바이트(8비트) 혹은 워드(16비트) 단위로 엑세스 할 수 있다.(예- AX는 AH와 AL로 구성) 각각은 데이터를 다룰 때 구분없이 사용되거나, 각각 특별한 용도로 사용된다. 대개 다음 명령어에 사용될 임시 결과를 저장하는데 사용된다.

 

□ AX(Accumulation, AH + AL = AX)
 주로 산술 연산(덧셈(AND), 뺄샘(SUB), 곱셈(MUL), 나눗셈(DIV)), 논리 연산(AND, OR, XOR등)의 대상이 된다. C함수는 함수 내에서 계산한 값을 리턴 할 때 AX레지스터에 넣어서 리턴한다.
 
□  BX(Base, BH + BL = BX)
 메모리상에 있는 변환표의 시작 번지를 가리키거나, 간접 어드레싱 모드에서 오프셋 어드레스를 가리키는데 사용된다.
 
□ CX(Counter, CH + CL = CX)
 주로 카운터하는데 사용하며, 카운터로 사용 될 경우엔 다른 레지스터로 대체할 수 없다. 문자열(string)을 다루는 명령(MOVSB, SCASB 등)이나 루프 명령(LOOP, REP)에서 카운터로 사용하거나, 쉬프트 명령에서 쉬프트 수, 로테이트 명령의 로테이트 수를 나타내는데 사용한다.
 
□ DX(Data, DH + DL = DX)
Port로의 입출력 명령(IN, OUT)에서 포트 어드레스를 지정하거나, 곱셈,나눗셈 명령에서 상위워드를 저장하는 데이터 레지스터로 사용한다.

 

세그먼트 레지스터(Segment Registers)

 8086의 CPU레지스터는 16비트이다. 하지만 8086의 어드레스 핀수는 20개이다. 따라서 최대 1MB(2의 20승)의 메모리를 가질 수 있다. 16비트 레지스터로 지정할 수있는 최대 메모리는 64KB(2의 16승)이므로, 이러한 1MB의 메모리를 전부 지정할 수 없다. 해결 방법으로 나온 것이 1MB의 메모리를 64KB단위로 나누어 관리하는 것이다. 이렇게 나눈 64KB 메모리 공간을 세그먼트라고 하고, 이 세그먼트는 16의 배수인 메모리 주소에서만 시작한다. 이 세그먼트의 시작 주소를 저장하는 레지스터가 세그먼트 레지스터이다. 자세한건 뒤에 나올 세그먼티드 메모리에서 다룬다.

 

포인터 레지스터와 인덱스 레지스터(Pointer Registers, Index Register) 

 16비트 크기를 가지는 오프셋 레지스터이다. 범용 레지스터와는 달리 상위및 하위 바이트로 분리해서 사용할 수 없다. 세그먼트 레지스터만 가지고서는 64KB 메모리공간의 시작 주소밖에 표시할 수 없으므로, 각 세그먼트 내의 주소를 나타내기 위해 또 하나의 16비트 레지스터가 필요한데, 이때 사용되는 레지스터를 포인터레지스터 또는 인덱스 레지스터이다. (메모리에 대한 포인터로 사용된다.) 자세한건 뒤에 나올 세그먼티드 메모리에서 다룬다.


'80x86 프로세서' 카테고리의 다른 글

3장. 일반적인 개념들  (0) 2010.04.12
2장. 80386 프로세서 (3/3)  (0) 2010.04.12
2장. 80386 프로세서 (2/3)  (0) 2010.04.12
2장. 80386 프로세서 (1/3)  (0) 2010.04.12
1장. 8086/8088 프로세서 (2/2)  (2) 2010.04.12

+ Recent posts