DLNA에 대해서 좀 알아 보려고 했더니만 뜬금없는 uPNP가 나오네??? DLNA가 uPNP에서 파생되었다고 하는데...어쩐지 miniDLNA소스를 봐도 uPNP 밖에 안 나온다… 그래서 uPNP에 대해서 먼저 학습을 하고 DLNA로 넘어가야 겠다.


uPNP

Universal Plug and Play 로 마이크로소프트사에 의해 제안된 기술이란다. PnP랑 이름이 같길래, 난 그건줄 알았더니 거의 유사하다. PC에 연결해서 주변기기를 알아서 등록, 재생 하는 그 기술의 확장판이랄까?? 요건 네트워크에 딱 등록되면 네트워크 연동해서 !!! 사용이 가능 하게 해주는 기술이랄까???

여튼, 요즘같이 스마트 시대에 아주 적당한 기술이라 할 수 있겠다. 프린트, 라디오, 비디오, 스마트폰이 네트워크로 연결되서 서로 사용이 가능 하다면 얼마나 편하겠나~~~ 좋은 세상이야..

uPNP는 TCP/IP, SSDP, SOAP, GENA, HTTP, XML같은 통신 표준과 기술을 바탕으로 한다고 한다.

TCP/IP는 알겠는데 SSDP, SOAP, GENA는 또 뭐냐??? 점점 꼬리에 꼬리를 물고 알아야 할게 늘어난다 ㅡㅡ;;;




SSDP
Simple Service Discovery Protocol로 네트워크상 장치들을 찾기 위한 프로토콜.

이라는데, 이게 뭔 소린지…흠..그냥 프로토콜 인데(?)

네트워크 상에서 1900 포트로 브로드캐스트 를 하면 같이 연결된 장치들이 그에 응답하여 서로 장치의 IP주소를 획득. 이렇게 해서 서로 같은 네트워크 상에서 장치를 인식하게 해주는 프로토콜(?) 인가 보다.



SOAP

Simple Object Access Protocol로 HTTP, HTTPS, SMTP등을 사용하여 XML 기반의 메시지를 컴퓨터 네트워크 상에서 교환하는 형태의 프로토콜이다.

요건 모.. 그냥 XML 데이터를 HTTP, HTTPS, SMTP 프로토콜로 서로 전송, 수신 한다는 말이고…



GENA

General Event Notification Architecture는 이벤트를 HTTP로 송.수신 한다.

뭔말인지… 그냥 이벤트를 HTTP를 통해서 전달한다는 말이겠지… 이벤트 전용 프로토콜인건가??



정리하믄 SSDP로 각 장치를 찾고, SOAP으로 데이터를 송수신 하고 GENA로 이벤트를 송수신 한다는 말인건가?

 



uPNP는 검색, 서술???(Description), 제어, 이벤트?(Eventing), 프리젠테이션  요런 단계로 나뉘어 진단다..




검색

Control Point 라는 놈(장치를 제어하는 놈)이 동일 네트워크 상에 장치(서비스 하는 기기)를 검색할 때 사용하나 보다. (사용할려면 어떤놈들이 있는지 부터 알아야 하니… ㅋㅋㅋ) 근데 Control Point 놈만 이걸 보내는 게 아니라, 장치 들도 네트워에 연결되면 알아서 ㅋ “나 여기 있어요~~” 라고 통지 메시지를 보낸다고 한다. 제법 기특해!~

Control Point는 M-SEARCH 메시지를 보내는데 “이 네트워크 있는 기기 들 있으면 모두 손!!!” 과 같다고 봐야 할 것 같다. 손 들라고 했으니 이 메시지를 수신 한 기기들은 Control Point로 응답 메시지(“저 여기 있어요~~~”)를 보낸다.

M-SEARCH * HTTP/1.1
HOST: 239.255.255.255:1900
MAN: “ssdp:discover”
MX: 30
ST: ssdp:all


M-SEARCH * HTTP/1.1 기기찾는 다는 M-SEARCH와 HTTP/1.1 버젼 정보
HOST: 239.255.255.255:1900 uPNP에서 약속된 브로드캐스팅 IP와 포트.
MAN: “ssdp:discover” 요건 필수!
MX: 30 Control Point라는 놈이 검색 한다고 하고 무한정 기다릴 수 없으니… 초 단위로 1에서 120 사이에 값.
ST: ssdp:all 네트워크에 있는 모든 장치 그리고 서비스를 찾는다. 문서를 보면 ssdp:all이 아닌 특정 장치, 특정 서비스(?)등을 찾는 세부적으로 나눠서 검색 할 수 있는 것 같은데.. 세부적인 내용에 대해선 뭔지 모르겠다…

M-SEARCH * HTTP/1.1 : HOST: 239.255.255.255:1900 uPNP에서 약속된 브로드캐스팅 IP와 포트 요건 안 바뀐다.

Control Point는 요런 형태로 네트워크 상에 있는 기기를 찾는다고 메시지를 보낸다.


HTTP/1.1 200 OK
CACHE-CONTROL: max-age=100
DATE: Tue, 18 Jun 2013 03:05:18 GMT
EXT:
LOCATION: http://192.168.10.100:8080/api/test.xml
SERVER: Linux/2.6.18 UPnP/1.0 Test Device/2.0
ST: ssdp:all
USN:



HTTP/1.1 200 OK HTTP 버전 및 응답
CACHE-CONTROL: max-age=100 장치가 Control Point 한테 본인이 유효한 시간(초 단위로 최대 1800)을 표기한다. 뭔말이냐 .ㅡㅡ;;; 이 시간 만큼 Control Point가 요청하는 내용에 대해서 응답을 할 수 있다는 말인가?? 흠.
DATE:Tue, 18 Jun 2013 03:05:18 GMT 응답 메시지가 만들어진 날짜/시간.
EXT: 요건 나도 몰라.
LOCATION: http://192.168.10.100:8080/api/test.xml 요 밑에서 언급될 서술? 설명? (Description)에 대한 장치의 정보를 담고 있는 위치.
SERVER:Linux/2.6.18 UPnP/1.0 Test Device/2.0 OS/버전, 장치/버전등의 정보.
ST: ssdp:all M-SEARCH의 ST 값에 의해 달라진다. 위에서 ssdp:all 이라고 했으니 ssdp:all 이라고 했다.
USN 서비스 이름. 식별자 인것 같기도 하고.. 몰겠어..

그러면 각 장치들은 요렇게 메시지를 만들어서 Control Point에 응답한다.

 

위에서 장치들이 네트워크에 연결이 되면 알.아.서 본인들이 통지 메시지를 보낼 수도 있다고 했다.

NOTIFY * HTTP/1.1
HOST: 239.255.255.250:1900
CACHE-CONTROL: max-age=100
LOCATION: http://192.168.10.100:8080/api/test/xml
NT: upnp:rootdevice
NTS: ssdp:alive
SERVER: Linux/2.6.18 UPnp/1.0 Test Device/2.0
USN: ~~~


NOTIFY * HTTP/1.1 장치가 알아서 응답한다.
HOST: 239.255.255.250:1900
NT: upnp:rootdevice upnp:rootdevice라는 놈이 보냈다 정도???
NTS: ssdp:alive 요렇게 명시해 줘야 한단다.

그래, “나 여기 있어요” 라고 보내는 참으로 기특하다. 근데 네트워크에서 제거 될 때도 알아서 통지 메시지를 보낸다.

NOTIFY * HTTP/1.1
HOST: 239.255.255.250:1900
NT: upnp:rootdevice
NTS: ssdp:byebye
USN: ~~~


NTS: ssdp:byebye 제거 될때 요렇게 해줘야 한단다.




서술? 설명? (Description)

Control Point 가 이제 네트워크 상에서 장치들이 어디(IP)에 있는지 알았다. 근데 이놈들이 정확히 어떤 놈들인지에 대한 확실한 정보는 없다. 그래서 검색 시에 장치들이 응답한 데이터 중 LOCATION 위치에 있는 정보(UTF-8 로 인코딩 되어 있단다)를 요청한다. 그냥 HTTP 프로토콜 GET 이다.

근데 이게 ㅡㅡ;;; XML 로 많은 내용이 있다.

<?xml version="1.0"?> 
 <root xmlns="urn:schemas-upnp-org:device-1-0"> 
 <specVersion> 
 <major>1</major> 
 <minor>0</minor> 
 </specVersion> 
 <URLBase>base URL for all relative URLs</URLBase> 
 <device> 
 <deviceType>urn:schemas-upnp-org:device:deviceType:v</deviceType> 
 <friendlyName>short user-friendly title</friendlyName> 
 <manufacturer>manufacturer name</manufacturer> 
 <manufacturerURL>URL to manufacturer site</manufacturerURL> 
 <modelDescription>long user-friendly title</modelDescription> 
 <modelName>model name</modelName> 
 <modelNumber>model number</modelNumber> 
 <modelURL>URL to model site</modelURL> 
 <serialNumber>manufacturer's serial number</serialNumber> 
 <UDN>uuid:UUID</UDN> 
 <UPC>Universal Product Code</UPC> 
 <iconList> 
 <icon> 
 <mimetype>image/format</mimetype> 
 <width>horizontal pixels</width> 
 <height>vertical pixels</height> 
 <depth>color depth</depth> 
 <url>URL to icon</url> 
 </icon> 
XML to declare other icons, if any, go here
 </iconList> 
 <serviceList> 
 <service> 
 <serviceType>urn:schemas-upnp-org:service:serviceType:v</serviceType> 
 <serviceId>urn:upnp-org:serviceId:serviceID</serviceId> 
 <SCPDURL>URL to service description</SCPDURL> 
 <controlURL>URL for control</controlURL> 
 <eventSubURL>URL for eventing</eventSubURL> 
 </service> 
Declarations for other services defined by a UPnP Forum working committee (if any)
go here
Declarations for other services added by UPnP vendor (if any) go here
 </serviceList> 
 <deviceList> 
Description of embedded devices defined by a UPnP Forum working committee (if any)
go here
Description of embedded devices added by UPnP vendor (if any) go here
 </deviceList> 
 <presentationURL>URL for presentation</presentationURL> 
 </device> 
 </root> 
 

복잡하다… ㅡㅡ;; 이제 각 속성들을 살펴 봐야 겠다.


root xmlns ”run:schemas-upnp-org:device-1-0 같이 xmlns이 반드시 있어야 한단다.
specVersion major, minor major , minor 버전. major 는 반드시 1이어야 한다고 하네?
URLBase   Optional.
device   장치
deviceType   장치 타입이라는데 “urn:schemas-upnp-org:device:” 로 시작해야 한다고 한다.  타입이 뭔지 모르겠다. devicetype:v 이렇게 있는데 v는 버전 정보란다.
friendlyName   그냥, 최종 사용자를 위한 짧은 이름?
manufacturer   제조사
manufacturerURL   제조사 URL
modelDescription   모델 설명
modelName   모델 이름
modelNumber   모델 넘버
modelURL   모델 웹 사이트.
serialNumber   시리얼 넘버
UDN   유일한 장치 이름. 장치 식별자.
UPC   제품 코드
iconList   장치에서 사용하는 아이콘 리스트
  icon Control point UI에서 표시될 아이콘
  mimetype 아이콘 MIME TYPE “image/png”.
  width 가로
  height 세로
  depth depth
  url 아이콘 이미지 파일일 있는 URL 주소
serviceList   장치에서 제공하는 서비스들(?)^^
  service 무슨 서비스를 할 것인가를 설명한 건가?? 참 어려다잉.
  serviceType 말 그대로 서비스 타입. “urn:schemas-upnp-org:service:”로 시작 되어야 한다고 한다. devicetype처럼 servicetype:버전 이렇게 설정한다.
  serviceId 서비스 식별자. “urn:upnp-org:serviceId:serviceID” 요렇게 설정.
  SPCDURL 서비스 설명을 위한 URL
  controlURL 컨트롤을 위한 URL
  eventSubURL 이벤팅을 위한 URL
devicelist   장치 안에 장치가 또 있나 보다. 또 디바이스 리스트.
presentationURL   presentation을 위한 URL

 

휴 많다… 이제까지 root device라는 용어가 나오는데 root device가 메인 장비?? 장치를 말하나 보다. 그 장치안에 또 장치가 있는 모양. ㅎㅎㅎ

이제, 장치에 대한 정보를 알았으니, 장치가 가지고 있는 서비스 정보에 대해서 알아야 한다. 요게 장치에서 제공하는 서비스의 액션, 변수, 데이터, 범위, 이벤트등의 정보를 가지고 있다고 한다. 그러니까 장치를 제어 하기 위해 필요한 정보 모음집으로 봐야 하나?? 하~~ 망할 영어…

Control Point는 장치 기술, 설명(description)을 HTTP GET으로 요청하고 다시 서비스 Description을 요청(HTTP GET)한단다.

 

<?xml version="1.0"?> 
 <scpd xmlns="urn:schemas-upnp-org:service-1-0"> 
 <specVersion> 
 <major>1</major> 
 <minor>0</minor> 
 </specVersion> 
 <actionList> 
 <action> 
 <name>actionName</name> 
 <argumentList> 
 <argument> 
 <name>formalParameterName</name> 
 <direction>in xor out</direction> 
 <retval /> 
 <relatedStateVariable>stateVariableName</relatedStateVariable> 
 </argument> 
Declarations for other arguments defined by UPnP Forum working committee (if any)
go here
 </argumentList> 
 </action> 
Declarations for other actions defined by UPnP Forum working committee (if any)
go here
Declarations for other actions added by UPnP vendor (if any) go here
 </actionList> 
 <serviceStateTable> 
 <stateVariable sendEvents="yes"> 
 <name>variableName</name> 
 <dataType>variable data type</dataType> 
 <defaultValue>default value</defaultValue> 
 <allowedValueList> 
 <allowedValue>enumerated value</allowedValue> 
Other allowed values defined by UPnP Forum working committee (if any) go here
 </allowedValueList> 
 </stateVariable> 
 <stateVariable sendEvents="yes"> 
 <name>variableName</name> 
 <dataType>variable data type</dataType> 
 <defaultValue>default value</defaultValue> 
 <allowedValueRange> 
 <minimum>minimum value</minimum> 
 <maximum>maximum value</maximum> 
 <step>increment value</step> 
 </allowedValueRange> 
 </stateVariable> 
Declarations for other state variables defined by UPnP Forum working committee
(if any) go here
Declarations for other state variables added by UPnP vendor (if any) go here
 </serviceStateTable> 
 </scpd> 

 


요놈도 장난이 아니다. 그냥 하나 하나 뜯어서 살펴 볼려니, 심신이 괴롭다. 아니 정확히 머리가 아프다..

 

scpd   반드시 urn:schemas-upnp-org:service-1-0으로 시작해야 한단다.
specVersion major, minor major, minor 버전 정보. major는 반드시 1이어야 한단다.
actionList   액션(?) 리스트?
action name 액션 이름. 동작 함수 인듯.
argumentList   액션이 함수라면 인자도 있겠지~~ 그 인자 리스트 정의.
argument name 인자 이름.
  direction 인자가 IN 타입인지 OUT 타입인지를 말하나 보다. IN, OUT 개념도 있네..흠.
  retval 액션 리턴 값.
  relatedStateVariable 액션 내부에서 사용할 StateVariable 이름??? 아직 모르겠다.
serviceStateTable   변수 테이블?
stateVariable name 변수 이름
  dateType 데이터 타입
  defaultValue 기본 값
allowedValueList allowedValue. 문자열에서 쓰나 본데 모르겠다.
allowValueRange minimum, maximum,step 변수값에 최소, 최대 값 정의.


휴~ 요렇게 해서 Description 마쳤다.

 

Control Point는 장치를 제어 하기 위한 정보를 Description을 통해서 다 얻었다. 이제 장치를 제어해 봐야 겠지~~




제어

장치의 제어는 서비스 Description에서 얻은 액션이름(함수명??)으로 가능하단다. 근데 위에서 언급했듯이 SOAP이라는 놈으로 구성되어 있다.(아~~ 망할…)

POST path of control URL HTTP/1.1 
 HOST: host of control URL:port of control URL
 CONTENT-LENGTH: bytes in body
 CONTENT-TYPE: text/xml; charset="utf-8" 
SOAPACTION: "urn:schemas-upnp-org:service:serviceType:v#actionName" 




---------body ----------
 <?xml version="1.0"?> 
 <s:Envelope
 xmlns:s="http://schemas.xmlsoap.org/soap/envelope/" 
s:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"> 
 <s:Body> 
 <u:actionName xmlns:u="urn:schemas-upnp-org:service:serviceType:v"> 
 <argumentName>in arg value</argumentName> 
other in args and their values go here, if any
 </u:actionName> 
 </s:Body> 
 </s:Envelope>

장치 제어는 HTTP 헤더와 body 요렇게 두 부분으로 구성되어 있다.

POST control URL HTTP/1.1 장치 Description에서 설정된 control URL.
HOST IP 주소, 도메인.
CONTENT-LENGTH body 크기
CONTENT-TYPE text/xml; charset=”utf-8” 로 사용하란다.
SOAPACTION urn:schemas-upnp-org:service:serviceType:번호#액션이름 이렇게 사용하란다. 뭔말인건지.. 제어할 액션이름.

헤더는 이렇고 body는…

 

Envelope   이건 그대로 쓰면 되겠다.
body   제어 부분
actionName   제어할 액션 이름을 쓴다.
xmlns:u=”urn:schemas-upnp-org:service:serviceType:v” 요건 모르겠다. 아놔 환장하겠네..
  argumentName 인자 이름. 인자 이름을 쓰고 해당 인자에 값을 표기.

근데 이렇게 장치로 POST 했는데 “405 Method Not allowed” 라는 메시지를 리턴 받으면 다시 M-POST로 메시지를 보내야 한다고 하네?  뭐이리 복잡해.

 

M-POST path of control URL HTTP/1.1 
 HOST: host of control URL:port of control URL
 CONTENT-LENGTH: bytes in body
 CONTENT-TYPE: text/xml; charset="utf-8" 
 MAN: "http://schemas.xmlsoap.org/soap/envelope/"; ns=01
01-SOAPACTION: "urn:schemas-upnp-org:service:serviceType:v#actionName" 

 

자.. 이제 제어 명령을 보냈으니, 장치가 응답을 보내겠지. 주는게 있으니 받는것도 있는 법이니까..

 

 HTTP/1.1 200 OK 
 CONTENT-LENGTH: bytes in body
 CONTENT-TYPE: text/xml; charset="utf-8" 
 DATE: when response was generated
 EXT: 
 SERVER: OS/version UPnP/1.0 product/version


--------- body ----------

 <?xml version="1.0"?> 
 <s:Envelope
 xmlns:s="http://schemas.xmlsoap.org/soap/envelope/" 
s:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"> 
 <s:Body> 
 <u:actionNameResponse xmlns:u="urn:schemas-upnp-org:service:serviceType:v"> 
 <argumentName>out arg value</argumentName> 
other out args and their values go here, if any
 </u:actionNameResponse> 
 </s:Body> 
 </s:Envelope> 

여기서 actionNameResponse는 actionName + Response 가 더해서 만들어진 단어인가 보다.  그렇다고 하니 그렇겠지.

 

제어는 대충 이런식인가 보다. 액션을 호출 하는 것만 알아 볼련다. 각 변수값들도 요청하는 게 있나 본데 솔직히 귀찮다. DLNA 수정해 보려다 uPNP때문에 미치겠다. 그래서 더 미치기 전에 간단하게 넘어 갈련다.

 



이벤트

Control Point가 장치의 서비스 변수의 상태가 변경이 되었을 때 통지 받고자 하면 이벤트를 요청한다고 한다. 장치 서비스는 변수의 값이 변경이 될 때마다 Control Point에게 이 값을 전달 하는게 이벤트 라고 한다.

Subscriber, publisher 뭐 이런놈들이 있는데 이건 그냥 무시하겠다… 깊게는 들어가지는 들어가지 말아야지^^

그럼 Control Point가 장치에게 이벤트 요청 메시지를 어떻게 보내냐면..

SUBSCRIBE publisher path HTTP/1.1 
 HOST: publisher host:publisher port
CALLBACK: <delivery URL> 
NT: upnp:event
 TIMEOUT: Second-requested subscription duration 

이렇게 보낸단다.

SUBSCRIBE publisher path HTTP/1.1 SUBSCRIBE 명령에 장비 Description에서 설정되었던 이벤트 URL 을 설정.
HOST 장치 IP, 포트
CALLBACK 이벤트를 전달받을 URL로 설정. 이때 이 URL은 여러개가 될 수 있다. 이벤트 메시지를 보낼곳들을 설정한다.
NT upnp:event
TIMEOUT 이벤트 발생시 한번 보내고 끝내는게 아닌가 보다. 이 timeout 값에 의해 보내는 시간이 결정된단다. Second-XX 이렇게 설정하던지 아니면 infinite 무한 설정 이렇게 한단다.

이벤트 설정? 메시지 수신 후 장치는 응답 메시지를 보낸다. 뭐~ 잘 받았다는 메시지 겠지..

HTTP/1.1 200 OK 
 DATE: when response was generated
 SERVER: OS/version UPnP/1.0 product/version
SID: uuid:subscription-UUID
 TIMEOUT: Second-actual subscription duration 

이 메시지중 SID 이 필드값 이건 아마도 이벤트 요청을 한 Control Point의 식별자를 장치가 하나 발급하나 보다. 이 SID 필드 값으로 관리하는듯… Control Point가 이 메시지를 수신 후 SID 값을 저장해 놔야 하나 보다.. 왜? 그건 renewal 메시지에서 사용하니까~~

SUBSCRIBE publisher path HTTP/1.1 
 HOST: publisher host:publisher port
SID: uuid:subscription UUID
 TIMEOUT: Second-requested subscription duration 

renewal 메시지는 이벤트 요청 메시지랑 명령은 같다. 다만 NT와 CALLBACK만 빠져 있다. 아~ SID 가 추가 되어 있다. 그럼 renewal은 뭐냐?? 단순히 메세지만 봐서는 TIMEOUT 값만 다시 변경 할 때 사용하나 보다. 추가된 SID는 장치에서 송신한 SID 필드값이겠지?? ㅋ 그러므로 Control Point도 SID값을 저장해 놔야 하는듯.

이벤트를 보내 달라고 했으니 보내지 말라는 메시지도 있겠지? 당연히~~ 있네…

UNSUBSCRIBE publisher path HTTP/1.1 
 HOST: publisher host:publisher port
SID: uuid:subscription UUID

이렇게 보내면 장치는 이벤트 메시지를 보내지 않는다고 한다.


이벤트를 요청하고 갱신?하고 이벤트 중지 하는 메시지 까지 했으니 이제 실제 이벤트 발생시 보내지는 메시지만 남았다.

NOTIFY delivery path HTTP/1.1 
 HOST: delivery host:delivery port
 CONTENT-TYPE: text/xml 
 CONTENT-LENGTH: Bytes in body
NT: upnp:event
NTS: upnp:propchange
SID: uuid:subscription-UUID
SEQ: event key


---------- body ----------------------

 <?xml version="1.0"?> 
 <e:propertyset xmlns:e="urn:schemas-upnp-org:event-1-0"> 
 <e:property> 
 <variableName>new value</variableName> 
 </e:property> 
</e:propertyset>

생김새는 제어 쪽에서 본 메시지랑 비슷하다.

NOTIFY delivery path HTTP/1.1   NOTIFY 요건 통지 관련 메시지다는 의미일테고 delivery path는 이벤트 요청시 설정한 CALLBACK url이란다.
CONTENT-TYPE   text/xml
CONTENT-LENGTH   body 크기
NT   upnp:event
NTS   upnp:propchange
SID   SID
SEQ   0에서 시작해서 1씩 증가한다고 한다.
propertyset   urn:schemas-upnp-org:event-1-0. 이렇게 써주고.
property variableName variableName변수의 변경된 값.

이벤트 메시지를 받았으니 메시지 잘 받았다고 응답 보내줘야지?

 HTTP/1.1 200 OK 

휴~~~

이 이벤트를 끝으로 uPNP는 그만 볼련다. DLNA를 시작으로 uPNP까지 머리도 터지겠고 보기도 싫다. 이거 뭐 되지도 않는 영어 문서 붙잡고.. 하나 하나 볼려니 오역80%에 개념 상실 20%.

그래도 uPNP 어느정도 개념은 잡았으니 miniDLNA 소스 코드는 어느정도 분석은 가능하겠군.. 근데 DLNA 프로토콜도 찾아서 봐야 하는데. 이 정도라면 그만 둘까 라는 생각이 든다.

 

참고문서:

http://upnp.org/specs/arch/UPnP-arch-DeviceArchitecture-v1.0.pdf

 

  

밥 먹고 와서 인터넷 포털 들어가니 전기 요금 개편이 실시간 뉴스 검색어에 올라와 있다. 요즘 전기가 부족하다고 난리더니 올리려나 하고 생각이 들어 뉴스 기사를 봤다.

연료비 연동제 시행, 누진제 축소



연료비 연동

이거 기름값 오르면 올라가고 내리면 내려간다는 말인가?? 헉… 휘발유 가격과 유사하네.. 아놔!! 더 비싸 지겠다… 휘발유 가격이 오를때 확, 내릴 때 찔끔찔끔 내리듯… 골자는 연료비 연동은 전기세가 오른다는 말인듯 하다. 참 이런 거 기획 하는 사람들 머리 한번 좋아..
굳이 연료비 연동으로 시행하려면 기름값 오름폭에 대한 정확한 기준(언제 기름을 얼마에 샀고 전기세에 반영 시기를 언제 한다는 거하고, 반영 퍼센테이지 산술 계산) 정도는 명확히 구분 짓고 하자 좀…

 

누진제 축소

현 6단계에서 3단계로 축소 한단다.. 6단계가 어떻게 되나 싶어 검색해 봤다.


이렇게 단계별 요금이 책정되어 있다고 한다. 이걸

0~200kwh 구간은 현행 유지,
300~600kwh 구간 (왜 300~900이 아니지????)
900kwh 초과

요렇게 3단계로 축소 한다는 거다. 딱 보면 일반가정에서 많이 사용하는 300~600kwh 구간의 가정들은 혜택을 보는듯 하지만, 이거 분명히 기본료 올릴꺼다. 안그래도 부족한 전기. 3개로 나눠서 기본료 올리려는 수작.

아~ 그냥 전기세 인상에 관한 개편이었구나!!!




괜히 뉴스 기사 클릭했다. 이 시간에 낮잠이라도 자둘껄…

하하하

OECD보다 전기세 낮다는 OECD 드립 기사가 나왔다. OECD 없었으면 어쩔뻔?? ㅋㅋ 근데 실질적으로 가정용 전기요금은 OECD 평균 보다 높을껄?? 다만 산업용 전기요금이 OECD평균보다 턱 없이 낮으니… 둘이 합하면 OECD보다 낮게 보이는거지.

OECD 들먹이려면 OECD에 맞게 다른 세금(법인세,증여)들도 개편 좀 해보지~~~


'소소한 재미' 카테고리의 다른 글

아이폰 iOS 17.X 메시지앱 먹통  (0) 2024.06.30
설국열차를 보고&hellip;(스포 작렬)  (0) 2013.08.16
공주님 안기  (0) 2013.08.14
소프트웨어 GS 인증  (0) 2013.08.14
티스토리로 블로그 이전  (0) 2013.08.14


개인 파일 서버를 이용하기 위해서 저렴한 큐비보드(http://www.cubieboard.org/)를 샀다. SATA 인터페이스, HDMI, USB 등 집에서 파일 서버로 이용하기 딱 좋은 보드라 판단했다.

TV로 동영상 재생은 옵션이고 주로 파일 서버로 이용할 생각이었다. 한데 큐비보드에 삼바 설치하고 FTP 설치 했더니, TV로 영화보기가 욕심이 났다. HDMI로 TV랑 연결 해주면 편하긴 한데, 리모콘을 지원하긴 하지만 리모콘을 안샀고 TV리모콘이랑 큐비보드 리모콘 두개를 같이 조작하자니 편의성도 없는 것 같았다. 그래서 포기 하려고 한 순간, LGTV가 DLNA를 지원한다고 한다.

DLNA는 Digital Living Network Alliance의 약조로서 DLNA인증을 통한 제품간에는 네트워크를 통하여 제조사와 제품 종류에 관계 없이 다양한 미디어 컨텐츠(음악/사진/동영상)을 공유하고 재생 할 수 있도록 규약을 정의하는 단체.

다시 무슨 말이냐면, 네트워크로 동영상 및 음악, 사진을 일정한 프로토콜을 통해서 재생 할 수 있는 통신 규약을 제공한다는 말 인것 같다. 어떻게?? 라는 의문이 들었다. ㅎ 이래저래 사용 인터페이스를 보니 단순히 DLNA서버에 LGTV가 접속해서 파일 목록을 표시해 주고 선택한 파일을 동영상 일경우 그냥 TV에 있는 동영상 재생기로 재생하는 기능이었다. 네트워크 파일 재생하는 정도??? 라 이해 했다. 와!~~ 내 사용 목적에 딱 들어 맞는 기능이다. HDMI 케이블 연결 할 필요 없이 서버랑 같은 네트워크에 물려 있으면 된다. 호 .. 이게 아이폰, 아이패드등 스마트 기기랑도 연결이 된다고 한다(뭐…난 TV로만 볼꺼니… 이런건 그냥 옵션…). 그럼 큐비보드(리눅스 기반)에 실행될 서버만 찾으면 된다.. 하지만 이게 쉽지 않았다…

이래저래 검색한 결과 miniDLNA

SRT 자막만 지원한다고 하는데 자막까지 지원하는게 어디냐… SRT는 차후 SMI에서 SRT로 변환하는 스크립트로 해결 될터이니..

설치하고 동영상 파일 옮겨 놓고…

실행!!!

TV에 외부 입력장치에 DLNA서버가 떴다. 아~~~ 이렇게 편하다니,…

동영상 파일 선택후 재생..



아~주 만족 스럽다..!!!

파일서버 기능과 동영상 서버 기능 이 되는 큐비 보드 만족한다.

영상을 다루는 사람들은 FFMPEG 라이브러리를 모르는 사람을 없을 것이다. 그래.. 많다. 안 쓰이는 곳이 없으니 웬만한 동영상 플레이어도 FFMPEG 라이브러리를 사용해서 재생한다. 물론 Directshow 를 이용해서 하기도 하지만 Directshow의 ffdshow도 FFMPEG 라이브러를 사용하니…

이 라이브러리는 방대하다. 웬만한 코덱은 다 지원하다 보니 덩치가 겁나 크다. 그런데 한동안 libav 라고 해서 잠시 분리되어 프로젝트가 진행되기도 하다 보니 API 인터페이스가 다른(?) 상황도 있었다. 뭐 지금은 다시 통합되었지만… 구글에서 ffmpeg 관련에서 문의 하다 보면 관련 샘플 코드가 어떤건 libav , 어떤건 ffmpeg 으로 작성되어 있는 경우도 있었다. 뭐 그다지 크게 다르진 않고 조금 다르긴 하지만 헷갈렸던 건 사실이다.

FFMPEG 라이브러리를 이용한다는건 어떤 파일을 다른 파일 포맷으로 변환 한다던지(재인코딩), 영상 스트림을 디코딩, 인코딩을 사용하기 위해서 일것이다. 여기서 난 윈도우 기반에서 개발한다는 가정하에 디코딩,인코딩 API 만 짚을 예정이다.


개발환경

- Windows 32bit
- Visual Studio 2010

FFMPEG 라이브러리 구하기

FFMPEG라이브러리를 사용하기 위해선 파일을 다운 받아야 한다. FFMPEG 라이브러리는 리눅스 기반에서 개발되었으며, 거의 모든게 GCC 컴파일러에 맞춰 있다. 물론 윈도우에서 컴파일 하는 방법은 있지만 그 방법이 쉽지는 않다. 많은 사람들이 어려웠던지 윈도우용 DLL 만 따로 모아놓은 사이트가 있다.

http://ffmpeg.zeranoe.com/builds/ 

여기에 윈도우용 ffmpeg 라이브러리 DLL 파일이 있다. 32 비트 파일과 64비트 파일 둘 다 지원한다. 또한 static, share, dev 용으로 구분 되어져 있는데 share과 dev용을 다운 받는다.

dev 압축파일을 적당한 위치에 압축을 풀어준다. 그리고 share 압축 파일에서 BIN 디렉토리의 DLL만 선택 후 dev 압축이 풀린 폴더에서 lib 폴더에 복사한다. dev 압축 파일에 include 파일과 lib 파일만 공개하고 실행시 필요한 DLL 파일은 share에서 포함되어 있기 때문이다.

개발환경

Visual Studio에서 ffmpeg 라이브러릴 사용하기 위해서 프로젝트 속성설정에서 DEV 압축 풀린 폴더에서 include 및 DLL 파일을 설정한다.

프로젝트 속성->C/C++ –>일반 –> 추가 포함 디렉토리 –> DEV 압축 푼 폴더/include

그리고 관련 lib 연결 소스 코드 Stdafx.h에서 연결했다.

   1: #include "ffmpeg/include/libswscale/swscale.h"
   2: #include "ffmpeg/include/libavformat/avformat.h"
   3: #include "ffmpeg/include/libavformat/avio.h"
   4: #include "ffmpeg/include/libavcodec/avcodec.h"
   7:  
   8: #pragma comment( lib, "ffmpeg/lib/avcodec.lib")
   9: #pragma comment( lib, "ffmpeg/lib/avformat.lib")
  10: #pragma comment( lib, "ffmpeg/lib/avutil.lib")
  11: #pragma comment( lib, "ffmpeg/lib/swscale.lib")

영상 디코딩

FFMPEG을 사용하기 위해선 인코딩 이던 디코딩이던 라이브러리를 초기화가 필요하다. 전체 프로그램에서 한번만 호출 해 주면 된다.

avcodec_register_all();

예전 버전에는 avcodec_init(); 함수도 있었지만 버전업 되면서 이 함수가 없어졌다.

영상을 디코딩 하기 위해서

AVCodec 과 AVCodecContext 두 변수가 필요하다.

AVCodec은 어떤 코덱(MPEG, MJPEG, H264)인지를 나타내는 정보를 가지고 있으며

AVCodecContext는 스트림을 어떻게 디코딩 할 것인지 정보를 가지고 있다.

이 두 변수를 각각 전역이든 멤버 변수든 선언해 준다.

   1: AVCodec *                m_codec;
   2: AVCodecContext *        m_context;

그리고 각 변수를 초기화 해준다.

   1: m_codec = avcodec_find_decoder(CODEC_ID_H264);
   2: m_context = avcodec_alloc_context3(m_codec);
   3: avcodec_get_context_defaults(m_context);

avcodec_find_decoder(CodecID)

이 함수는 디코딩 코덱을 선택해서 m_codec을 초기화 해준다. CodecID는 avcodec.h에 정의되어 있다. 여기선 H264 코덱을 선택했다.

avcodec_alloc_context3(AVCodec*)

이 함수는 m_context 변수를 초기화 해주는 함수로 AVCodec 정보를 가지고 context를 메모리에 할당한다. 계속 FFMPEG이 버전업 되면서 끝에 숫자가 증가하는 것 같다. 이유? 나도 모른다. 검색해서 찾아 볼 여유가 없었다. ㅋㅋ

avcodec_get_context_defaults(AVCodecContext*)

context 변수를 초기화 하는 함수이다. 호출 안해도 상관 없다. 왜??? avcodec_alloc_context3에서 초기화가 이루어 졌으니까..

초기화가 되었으니까, 이제 어떤 영상 스트림을 디코딩 할것인지 직접 입력해 줘야 한다.

   1: m_context->width = 320;
   2: m_context->height = 240;
   3: m_context->codec_id = CODEC_ID_H264;
   4: m_context->codec_type = AVMEDIA_TYPE_VIDEO;
   5: m_context->flags2 |= CODEC_FLAG2_FAST;
   6: m_context->thread_count = 0;

 

width, height는 320, 240이고, 코덱은 H264, AVMEDIA_TYPE_VIDEO로 비디오를 디코딩 한다는걸 설정하고 CODEC_FLAG2_FAST는 그냥 샘플 코드에 있어서 넣어 봤다. 빼도 상관 없다. thread_count 몇개의 쓰레드로 디코딩 하는지 명시하는 부분인데, 나도 모르겠다. 저 값에 10을 넣으나 1을 넣으나 속도는 같은 것 같은데 왜 적용이 안 되는지 모르겠다. 0은 라이브러리가 알아서 쓰레드 만든다 라고 FFMPEG 문서에 있다. 이것도 제대로 되는지 모르겠다. 흠흠…

설정 정보 다 입력했으면 최종 FFMPEG 라이브러리를 설정해야 한다.

   1: avcodec_open2(m_context, m_codec);

요렇게만 하면 이제 디코딩 하기 위한 준비는 다 끝났다.

이제 스트림 데이터가 있는 변수를 ffmpeg 라이브러리에 넘겨 주고 디코딩 시키면 된다.

   1: AVPacket avpkt;
   2:  
   3:  
   4: av_init_packet(&avpkt);
   5:  
   6: avpkt.data = pEncodedData;
   7: avpkt.size = EncodedSize;

예전 버전에서는 스트림 데이터를 바로 이용했는데 어느 순간 버전업 되면서 AVPacket을 이용해야 했다. av_init_packet으로 초기화 해주고 data와 size에 스트림 데이터, 데이크 크기를 전달 한다.

   1: int got;
   2: int ret;
   3: AVFrame *m_picture;
   4:  
   5: m_picture = avcodec_alloc_frame();
   6:  
   7: ret = avcodec_decode_video2(m_context,m_picture, &got, &avpkt );
   8:  
   9: if( got > 0 )
  10: {
  11:   ...........
  12: }

 

깜박하고 디코딩시 디코딩 된 이미지 데이터를 저장할 변수를 초기화 하지 않았다. ^^ avcodec_alloc_frame()으로 이미지 변수를 할당 받는다.

avcodec_decode_video2(AVContext*, AVFrame*, int *, AVPacket *)

스트림 데이터를 이미지로 변환하는 함수다. 만약 이미지로 변환이 성공하면 got 변수에 0 보다 큰 값을 리턴한다.



영상 인코딩

초기화 기본은 디코딩과 같다. 다만 avcodec_find_decoder가 avcodec_find_encoder로 변경되었을 뿐이다.

   1: m_codec = avcodec_find_encoder(CODEC_ID_H264);
   2: m_context = avcodec_alloc_context3(m_codec);
   3: avcodec_get_context_defaults(m_context);

그리고 압축을 하기위한 설정을 context에 입력한다.

   1:  
   2: m_context->bit_rate = 512*1024;
   3: m_context->bit_rate_tolerance = 512*1024*2;
   4: m_context->width = 320;
   5: m_context->height = 240;
   6: m_context->time_base.num = 1;
   7: m_context->time_base.den = 24;
   8: m_context->gop_size = 24;
   9: m_context->profile = FF_PROFILE_H264_BASELINE;
  10: m_context->pix_fmt = PIX_FMT_YUV420P; 
  11:  
  12: av_opt_set(m_context->priv_data, "preset", "fast", 0);
  13: av_opt_set(m_context->priv_data, "profile", "baseline", 0);
  14:  
  15:  

압축될 영상은 320, 240 사이즈로 설정하고 비트레이트는 512kbps 로 설정했다. 또한 FPS 24, GOP는 24다. 그리고 압축을 H264로 하기 때문에 프로파일은 BASELINE. 예전 버전에서는 없었는데 버전업 되면서 생긴 av_opt_set 으로 preset, profile을 설정했다. 뭐 이렇게 써라고 하니 썼다… 정확하지는 않는다. 그냥 인터넷에서 긁어 모으다 보니~~ ㅋㅋㅋ

   1: AVFrame* m_picture;
   2:  
   3: m_picture = avcodec_alloc_frame();
   4:  

디코딩과 마찬가지로 인코딩도 AVFrame 으로 영상 데이터를 입력 받는다. 그래서 AVFrame을 할당 받는다.

인코딩은 보통 YUV420P 로만 입력 받는다. RGB24로 입력 해봤지만 계속 실패해서 성공해 본적이 없다. 버전업 되면서 지원 되는지 모르겠지만.. 예전에는 안 되었다. 그래서 영상 데이터를 YUV420P 로 변환 해 줘야 한다.

   1: struct SwsContext *    m_convert_ctx;
   2: AVPicture dstpic;
   3: AVPicture srcpic;
   4:  
   5: m_convert_ctx = sws_getContext( 320, 240, PIX_FMT_BGR24, 320, 240, PIX_FMT_YUV420P, SWS_FAST_BILINEAR | SWS_CPU_CAPS_MMX, NULL, NULL);
   6:  
   7: avpicture_fill(&dstpic, m_YUVImageData, PIX_FMT_YUV420P, 320, 240);
   8: avpicture_fill(&srcpic, m_RGBImageData, PIX_FMT_BGR24, 320, 240);
   9:  
  10: sws_scale( m_convert_ctx, srcpic.data, srcpic.linesize, 0, 240, dstpic.data, dstpic.linesize);
  11:  

변환을 위해서 sws_getContext() 함수를 이용한다. sws_getContext()함수로 변환 핸들을 얻은 후 이 핸들을 sws_scale()로 실질적인 변환 작업을 한다. sws_getContext는 소스의 가로, 세로, 파일포맷, 변환할 가로, 세로, 포맷을 지정한다. sws_scale 함수는 소스 AVPicture를 변환 AVPicture로 변환해 준다. ㅋㅋㅋ 뭔 소린지 ㅋㅋㅋ

BGR24를 YUV420P로 변환 하였다. 이제 인코딩 하면 된다.

   1: int encoded_size = 0;
   2: BYTE *ENCODED_DATA = 1024*1024;
   3: int ENCODED_SIZE = 1024*1024;
   4:  
   5: avpicture_fill((AVPicture*)m_picture, m_YUVImageData, 320, 240);
   6:  
   7: encoded_size = avcodec_encode_video(m_context, ENCODED_DATA, ENCODED_SIZE, m_picture);
   8:  

자 요렇게 인코딩 하면 된다.

 

 

'프로그래밍 > C | C++' 카테고리의 다른 글

UPNP 프로토콜  (0) 2013.08.21
클래스 private, protected, public 멤버 및 상속  (0) 2013.08.14
클래스 가상함수, 순수가상함수  (0) 2013.08.14
윈도우 malloc  (0) 2013.08.14
RTPLIB 1.0b 라이브러리 예제  (0) 2013.08.14

  오늘 목요일 휴일(8월 15일 광복절)이다 보니 집에만 있기가 갑갑해서 바람 쐴 겸 영화를 보러 갔다. 흥행 순위 1위를 달리던 “설국열차”… 이래저래 논란(CJ가 제작/공급 해서인지 CGV 스크린을 독점 상영, 재미 없다 등등)도 있고 했었지만 내가 보고 판단하기 위해서 선택했다.

- 내용

지구의 온난화로 인해 세계 각국 정상들은 CW-7을 지구 전역에 살포 하게 된다. 그로 인해 오히려 역효과로 지구가 빙하기로 이르러 지구의 모든 생명체가 전멸이 되는 상황이 된다. 그러나 윌 포드가 만든 기차에 탑승 했던 사람들은 살아남아 지구상의 유일한 인류가 되게 된다. . . 윌 포드의 기차는 멈추지 않고 지구의 모든 대륙을 1년을 주기로 멈추지 않고 17년동안 달린다.

그리고 영화는 시작한다…

설국열차는 이렇게 칙칙한 화면으로 남루한 옷을 입은 사람들이 줄을 선 모습을 보여준다. 아~~ 살아 남은 사람들이 정말 힘들게 삶을 이어가고 있구나~ 라고 생각했다. 그런데 군인들의 등장. 그들은 이들을 통제하는 역활인건지 험악한 분위기로 이들의 수를 세기 시작한다.

이 양반(커티스)이 그 분위기에 반발 하듯, 그 모습을 지켜 보고 있다. 그리고 조만간 무슨 사건을 일으킬 듯한 분위기를 풍긴다.

커티스에 반발에 동조한듯한 에드가가 그를 “지금 시작하자” 라고 부추긴다. 하지만 커티스는 아직은 아니다 라고 그를 타이른다. 여기까지 이 영화는 노예의 반란을 보여주는듯 진행된다..

줄을 선 사람들이 인원 파악이 끝난후 요렇게 생긴 단백지 블록 이라는 먹을 음식을 하나씩 가져가며 먹는다. 그러면서 영화는 마지막 칸의 사람들은 열악하게 살고 있고, 그 앞칸의 사람들은 호위호식 하며 살고 있다는 분위기를 설명한다. 또한 마지막 칸의 사람들은 이 불공평한 상황과 학대에 불만을 가지고 있고 반란을 계획하고 있다는 걸 보여준다.

커티스는 앞칸의 동조자가 보낸 쪽지로 이 반란에 “남궁민수”라는 기차의 보안설계자가 필요하다는 지령을 받게 된다. (앞칸 까지 가기 위해 문을 열 사람…) 그러던중

타냐(위 사진의 여자), 앤드류(사진의 남자)의 각각의 아들들을 앞칸의 한 여자가 군인들을 대동하고 데리고 가버리는 사건이 발생한다. 이때 앤드류는 군인들과 몸싸움을 하게 되었고… 형벌을 받게 된다.

한팔을 기차 밖으로 내밀게 해, 꽁꽁 얼린 후 얼린 손을 도끼로 깨버린다. 형벌 한번 잔인하다.

형벌이 진행하는 동안, 이 여자가 마지막칸의 사람들을 모아 놓고 위대한 윌포드에 대한 얘기와 사람은 각각의 위치가 있으며 마지막칸 사람들이 이 위치를 거역하고 있다고 말한다. 그리고 그 위치를 꼭 지켜야 한다고 말한다. 마지막칸 사람들은 점점 분노는 거세지고 드뎌 반란을 진행한다. 그리고 감옥에 있는 (감옥인지 시체 보관소인지 모를..) 남궁민수와 그의 딸을 꺼낸다.

그리고 억지설정의 통역기… 남궁민수가 한국 사람이다 보니 마지막칸 사람들과 대화가 필요 했고 이를 통역기로 해결해야 했는데… 낭궁민수. 송강호가 굳이 이 영화에서 필요했을 까?? 한국 사람이 등장할 필요가 있었나??

감독이 한국 사람이어서?? 아니면 CJ의 의해서??? 여튼.. 억지 설정 등장해 주신다…여튼 마지막칸 사람들은 기차를 장악하기 위해서 앞칸, 앞칸으로 이동한다. 앞칸으로 가면서 단백질 블록이 바퀴벌레로 만든 다는 사실에 경악하고..

앞칸에서 대기중인 백정(?),군인(?) 들과 싸우는 도중 위 사진 처럼 위험한 곳을 지나게 되면서 잠시 싸움 중단… 또, 싸움중 한 해가 지났다고 Happy New Year! 외쳤을 때… 실소!!! 대다수의 마지막칸 사람들이 죽게 된다.

이때, 마지막칸의 정신적 지도자 격인 길리엄이 사람도 많이 다쳤으니 물을 공급하는 칸을 차지 했으니 이쯤에서 그만하자고 커티스에게 제안한다. 하지만 이에 만족하지 못하는 커티스는 기차의 엔진까지 장악할 생각 인지라 이에 동의 하지 못한다. 그러자 길리엄은 기차의 엔진에 있는 윌포드를 만날 경우, 말할 시간을 주지 말고 바로 죽일 것을 당부한다. (왜??? ㅋㅋㅋㅋ 요게 반전이란다. 반전치고는 재미없다…)

아들들을 뺏아긴 몸이 날렵한 싸움꾼 그레이, 타냐, 앤드류, 남궁민수, 그의 딸 요나, 커티스 이렇게 소수 정예와 얄미운 연기를 한 메이슨의 앞칸 중간 보스격인 여자를 대동하고 다시 앞칸으로 이동한다.

앞칸으로 가면서 요렇게 생긴 정원을 지나치고 물고기들이 있는 수족관도 지나고 닭고기, 돼지고기가 있는  정육칸도 지나고 앞칸 어린이들이 교육 받는.. 학교칸도 지나간다.

요게 아이들이 교육받는 칸… 마지막칸 사람들의 대한 지배계층적 사상을 세뇌 받는 곳이다. 여기서 임신한 교사가 총까지 들어 쏜다!!! 물론 적중률 제로. 적중률이 제로 인지 소수 정예가 줄거리상 필요한지 아무도 죽는 사람이 없다. 단지 교사 본인만 그레이 칼에 맞아 죽는다. 여기서 열 받은 커티스는 메이슨을 죽이고 다시 앞칸으로 간다. 앞 칸 사람들의 사치 스러운 부분을 보여주며 앞으로 앞으로 전진. 소수정예 사람들이 필요 없는지 기차의 보안요원인지.. 경비원인지.. 군인인지 모를 프랑코에 의해 낭궁민수, 그의 딸 요나, 커티스만 빼고 다 죽는다…. ㅋㅋㅋㅋ 학교칸을 끝으로 나머지 사람들이 줄거리상 필요 없나 보다… 어이 없게 죽는다.. 이럴 거면 왜 데리고 가냐고… ㅋ 여튼… 커티스는 제일 앞칸 윌포드 문 앞까지 도착한다. 그리고 낭궁민수 에게 문을 열어 달라고 부탁하지만… 여기서 낭궁민수의 뜬금포!!! 본인은 앞 문 보다는 기차 옆문을 열고 싶다네??? 왜?? 기차가 답답해서 밖으로 나가고 싶다고… 아놔~~~ 여기까지 와서 앞을 안 열고 옆을 열고 싶데… ㅋㅋㅋㅋ 그러던중 윌포드의 하수인격인 아이들을 데리고 갔던 여자가 와서 커티스를 윌포드 앞으로 데리고 간다. 그리고 들어나는 재미없는 반전.. 길리엄은 윌포드와 가까이 있는 사람으로 마지막칸 사람들이 인원이 늘어날 때마다 반란을 부추겨 마지막칸 사람의 수를 줄이는게 그 역활 이라네.. 한마디로 뿌락지 였던 거지.. 여튼 어찌저찌해서 기차 옆문을 폭약으로 터트린 남궁민수… 그리고 그 폭발음으로 눈사태가 일어나고 기차는 그 눈사태로 인해 갈기 갈기 다 부셔진다. 사람들이 다 죽었는지 다쳤는지… 어찌 되었든 등장하는 사람은 남궁민수 딸 요나와 티냐의 아들만 남는다. 그리고 기차 밖으로 나오면서 영화는 끝난다.

이 영화의 내용은 이게 다다. 물론, 영화에서 던지는 메시지는 있지만 그 주제가 복잡하진 않다. 그냥 보면 메시지를 보게된다. 그렇다고 생각을 깊게 하거나… 여운이 남지도 않는다.

이 영화가 인셉션이나 매트릭스와 같은 급의 영화로 올려 놓는지 모르겠다. 솔직히 재미 없다.. 앞 칸으로 가는게 전부인 영화다. 클라이막스가 있었나 싶을 정도로 지루했다..

언플과 평점 알바에 속은 듯한 느낌이다.

내 평점

★★☆☆☆ 별 두개..

'소소한 재미' 카테고리의 다른 글

아이폰 iOS 17.X 메시지앱 먹통  (0) 2024.06.30
전기요금 개편  (0) 2013.08.21
공주님 안기  (0) 2013.08.14
소프트웨어 GS 인증  (0) 2013.08.14
티스토리로 블로그 이전  (0) 2013.08.14

예전에 만들었던 “공주님 안기” 플래시

그때 당시 너무 웃겨서 애니메이션에서 추출해서 만든건데 지금 봐도 웃기다.




어랏~ 어랏~ 하는 소리가 너무 귀에 생생해!!! ㅋㅋㅋ

'소소한 재미' 카테고리의 다른 글

전기요금 개편  (0) 2013.08.21
설국열차를 보고&hellip;(스포 작렬)  (0) 2013.08.16
소프트웨어 GS 인증  (0) 2013.08.14
티스토리로 블로그 이전  (0) 2013.08.14
두껍아 두껍아 헌집줄께 새집다오!  (0) 2013.08.14

GS 인증

소비자와 기업이 우수한 SW제품을 보다 잘 믿고 쓸 수 있도록, 일련의 시험 테스트 과정을 거쳐, 일정한 수준의 품질을 갖춘 SW제품에게 국가가 부여하는 인증제도.

GS 인증을 받았을 때 혜택

1. 품질이 개선되고 비용 절감 ( 제 3자가 시험인증을 통해 단기간 획기적인 품질 개선과 비용 및 시간 절감)

2. 마케팅 / 홍보 용이

3. 다양한 제도적 혜택

  - 조달청 3자 단가 계약 체결 및 나라 장터 등록

  - GS인증 제품 우선구매제도 시행

  - 중소기업청 성능 인증 시 성능검사 면제

  - 저렴한 요율의 성능 보험 제도 및 공공기관 구매자 면책제도 시행

  - 지방자치 단체의 도로 및 상.하수도 시설물관리를 위한 GIS 소프트웨어 GS 인증 의무화

  - 경찰청 학사관리 시스템 GS인증 의무화

  - 신SW 상품 대상 수상작 GS인증 의무화

  - 소프트웨어 기술성 평가 면제 및 소프트웨어 기술제안서 평가 시 가산점 부여

  - 전자정부 사업 기술 제안서 평가 시 가산점 부여

  - 국방부 정보체계 개발 사업 추진 시 GS인증 제품 우대 권고

  - 기획재정부 세출예산집행지침 개정

 

GS 인증 신청

- 신청서 작성

- 시험방법, 시험일자 조정 및 GS 인증비용 산출

- GS인증비용 결제

GS 인증 시험

- 제품설명서 및 제품 메뉴얼 작성

- 협회로 부터 시험일자 통보

- 시험일자에 장비 또는 소프트웨어 협회에서 준비한 컴퓨터에 설치

- 제품설명서 및 제품메뉴얼 협회 전달.

- 1~2주 동안 협회에서 소프트웨어 테스트 (폰트 크기부터 위치, 등의 아주 자세한 부분까지 테스트)

- 협회에서 테스트 시 발생한 소프트웨어 문제점을 개선 하도록 통보 (상,중,하 구분하여 전달)

- 협회에서 심사에 관련한 자료 요구 (자료 하나하나 점수에 해당 하므로 가능한 모두 제출)

  1) 회사 전체 조직도, 사업자등록증 사본, GS 신청 제품 주요 납품처 계약서 사본, 특허증 (존재시)

  2) 기술개발 전담인력이 표시된 조직도(부서명. 부서사원등의 인원 현황이 파악 가능 조직도), 기술 부설 연구소 인증서

  3) 요구사항명세서, 컨설티 의뢰 문서, 고객설문 조사, 피드백 조사, 고객만족도 조사 자료, 국내외 시장 흐름 분석과 관련된 조사 자료, 요구사항 분석 및 통계 내역서, 요구사항을 분석한 자료, 요구사항 분석 매뉴얼 및 분석 기술 메뉴얼.

  4) 개발관리 조직 운영매뉴얼, 개발관리 업무 프로세스 명세서, 품질 경영 매뉴얼, 계획~인도 등의 개발 관리 체계를 보여줄 수 있는 자료, 개발산출물(상세설계서)

  5) 제품의 형상관리 목록, 제품 제작 및 배포 매뉴얼

  6) 제품 개발 업그레이드 내역서

  7) 기술개발 장비 자체 보유 목록(HW,SW,NW등 개발 관련 보유 현황 자료)

  8) 시험 전담인력이 표시된 조직도

  9) 유지보수 점담 인력이 표시된 조직도, 유지보수 이력 및 현황 목록, 유지보수 지원체계 명세서, 운영 매뉴얼

  10) 교육 지원체계 명세서, 운영매뉴얼

  11) 적용된 SW 개발 방법론 관련 자료,

  12) SW 품질 관리 공정에 관한 매뉴얼

- 최종 인증 심사(1~3주)

어렵지??? 어려워!! 이거!!!

이거 인증 시험 대응하기 정말 어려워!!!

프로그램만 가져다 주면 되는 줄 알았지만, 관련 문서 작성도 필요하고 정말 자세히 테스트 한다. 생각지도 못한 부분을 찾아서 개선 요구한다. 와~~ 비싼 값을 하지만.. 죽을 맛..

근데, 다들 쉬운 줄 안다.

이 GS인증을 준비 할 생각이면 1달을 죽었다 라고 생각해야 함.

 

 

구글, 다음에 블로그 등록해 놨더니, 스팸과 봇들이 대폭발 했다. 기존 400M의 트래픽으로 감당이 되지 않았다.

그래서 기존 설치형 블로그 “텍스트 큐브”를 그 좁디 좁은 웹계정에 만들게 한 원흉 티스트리. 이곳에 다시 초대장 구걸을 해 어렵게 티스토리에 들어왔다.  워낙에 변화를 싫어하는 스타일이라 스킨 부터 마음에 들지 않았고 인터페이스도 낯설고….

별수 있나…

음...
날강도 적인 말이다. 어렸을때 부터 이런 날강도적인
노래로 정신세계를 단련해서 이렇게 된걸까? ㅋ
이 노랫말에 유례의 대해서 찾아 봤는데
옴두꺼비 에 대해서 언급된 글이 있다.
옴두꺼비는 알을 품고 독사에게 먹이가 된다고 한다.
그리고 독사에 몸속에서 자식들이 나온다는 말인데!
두꺼비는 개구리처럼 하천이나 우물에 알을 낳을껀데
왜 알을 품는다는 말이 나온걸까?
아무리봐도 지어낸것 같은 냄새가 많이 품긴다.
그리고 옴두꺼비는 없다는 말이 언급이 되네..
판타지 세계 중국에서나 가능할까나? ㅋㅋ
어렸을때, 비오는 날 두꺼비는 자주 봤다.
항상 비오는 날에만 본듯한 느낌이다. 등이 화려한 뱀 무늬와 같은
디자인. 솔직히 지금은 손으로 집지 못할것 같은데
대담하게도 손에 집어서 가지고 놀았던 기억이 떠오른다.
비오는날 청승맞게 길에 나와서 나와 같은 어린아이의 손에서
장난감이 되었던 두꺼비. 지금 생각해보니, 많이 불쌍해 보인다.
비 맞고 뭐하는건지? . 비 맞으면서 무슨 생각을 하는건지.
그때 , 시절 내가 불행했는지, 아니면 정말로 두꺼비가
불쌍한건지 그 기억만 떠오르면 가슴이 지 맘대로 시키지도 않은데 운다.
비오는날 엉금엉금 도마뱀 마냥 도망가는 두꺼비.
비는 내리고 ......아마 나도 비 맞고 서 있었을꺼다.

-영화, 1번가의 기적을 보고.

SF 영화로 시간 때우기에 적당할 것 같아서 봤다...
로맨스나 코미디 장르를 빼고 또 이런 저런 액션 빼니 이것 밖에 없더라~^^

이 영화는 지구인의 화성이동에 앞서 연구 및 환경을 조성하기 위해
지구인이 화성으로 간다는 것부터 시작한다...
(남.여 부부가 우주 여행시 많은 도움이 되어서 부부동반 여행을 한다나 어쨌다나...)

화성한 도착한 팀들은 화성 이곳저곳을 탐사하다가
어느 산위의 얼음으로 판단되는 곳을 발견한다.(얼음 = 물 = 생명체 존재 가능성..)
그래서 차를 타고 그 산을 갔다가 그 산의 흙들이 다 쏟아지면서
한명만 남고 몰살당한다...

그리고 지구 위에 떠 있는 우주정거장에선 그 한명을 구하기 위해 구조팀 출발
그 구조팀도 화성에 탐사 하기전 불의의 사고로 한명을 잃고 화성에 도착...

다시, 그 산으로 간다.. 산에 흙들이 없어지고 사람 얼굴 모양의
구조물이 발견되고... 그 구조물과 살해된 사람들의 연관 관계를 찾고...
어렵다..설명이 ^^

여튼.. 그 구조물은 화성인이 만든걸로..
애초 화성이 행성과 충돌로 살기 힘든 환경이 만들어지면서
화성인들은 우주 곳곳으로 이동한다. 그러다가
지구에 화성인이 생명의 시작인 유전자를 지구에 보내고
지구가 진화 하여 사람까지 만들어지는 과정을 보여준다.

아~~
볼만하다...
CSI 에 나오는 아저씨의 황당 결정에 좀 연결부분이 부족할것 같긴 하지만..

소재 : ★★★★
재미 : ★★★
연기 : ★★

+ Recent posts