고등어가어딨니
577
2021-08-04 14:26:52
12
529

안드로이드 NFC 태그에뮬(HCE) <-> NFC 리더기 <-> 서버 문열고닫기 알고리즘


지금 어쩌다보니깐  안드로이드로 NFC 태그에뮬어플을 만들어야되는데 

어플을 켠상태에서  NFC 리더기에 갖다대서 정보가 맞으면 문을열고 틀리면 문을 안열어주는상황인데


제가 생각하는게 맞는지 검토 부탁드립니다

NFC리더기는 완전한 임베디드 분야라서  이쪽 돌아가는 원리를 모르겠네요 


<안드로이드 어플쪽>

HCE 형식 준수하여 설계 

AID = 1로 설정   (AID는 애플리케이션 고유 식별자)

URL = www.~~~~~~/com?id="kim"&pw="1234"  => NDEF화


<NFC 리더기>

AID = 1인 어플리케이션 탐색  탐색됬다면  그 어플에서 NDEF 추출 

(NDEF를 추출하면 바로 URL로 이동)


<서버>

POST 나 GET타입으로 들어온 값들을 DB조회함 정보가일치하면

JSON? 형식으로 reuslt값을  리더기에 보내줌   ( e.g   result="success")


<NFC 리더기>

결과값받고 success이면 문을 열어줌


이게맞나요 ??


0
  • 댓글 12

  • ruinnel
    540
    2021-08-04 14:57:50 작성 2021-08-04 15:04:36 수정됨
    제가 봤던 일반적인 케이스(NFC만 되고 인터넷 연결은 안되는 도어락)에서는..
    카드로 열리는 도어락과 동일하게..
    설정 모드에서 휴대폰에서 발행해주는 고유 식별값을 읽어서 도어락에 저장을 먼저 해두고..
    이후 휴대폰을 가져다 대면 열리는 방식으로 하는건 봤습니다.
    (이 경우 그냥 도어락 내부에 저장된 식별값과 대조 후 같으면 열어주는 방식 이겠죠.)

    NFC 리더기(도어락?) 도 인터넷 통신이 가능한 건가요?
    거기다 http 프로토콜까지?... 신기하네요.
    NFC 리더기 쪽이 http 통신까지 가능하다면 말씀하신 절차대로 수행 될거 같구요.

    추가로... 적어놓은 순서가 처리되는 순서?라면 NFC 리더기가 먼저입니다. 

    HCE는 카드를 에뮬레이션 하는거니 말그대로 passive로 동작합니다.


    HCE로 구현된 앱(android.nfc.cardemulation.HostApduService 를 구현한 서비스를 가지고 있는..)이 스마트폰에 설치되어 있으면..

    NFC 통신의 시작점은 NFC 리더기 쪽입니다.


    리더기에서 AID 지정해서 신호를 쏘는거구요.


    스마트폰이 그걸 받으면 AID를 식별해서 등록된 HostApduService 구현체 중에 AID에 맞는 서비스를 찾아서 통신 라이프사이클에 맞게 적절히 메소드를 호출 해줍니다(onDeactivated, processCommandApdu)


    스마트 폰에서는 HostApduService 상속받아서 구현한 각 메소드가 호출되면 필요한 동작을 구현하는거구요.

    단, processCommandApdu의 경우 ByteArray를 반환하고 그 반환한 값이 리더기가 수신하는 값이 되는데요.
    그래서 함수가 호출되고 너무 긴시간 동안 값을 반환하지 않으면 NFC 리더기와의 통신이 끊어지거나 할 수 있어서 데이터 수신 후 서버와 통신하고 그 결과를 반환하던가 하는 방식은 피하시는게 좋습니다.


    그리고 NFC 리더기와의 통신은 꼭 NDEF 메세지 규격을 따르지 않아도 상관없습니다.
    NDEF 메세지 규격에 각종 헤더들이 있어서 통신해야될 데이터만 많아지게 됩니다.


    NDEF 메세지는 스마트폰이 NFC로 정보를 읽어 들일때 URL이 포함되어 있으면 URL을 열어준다거나..하는 것처럼 스마트폰에서 무언가 동작을 시키기 위한 규약이라서..


    HCE로 스마트폰이 태그처럼 동작할때는 굳이 NDEF를 안쓰셔도 됩니다.
  • 고등어가어딨니
    577
    2021-08-04 15:17:49

    아이고 또 답변해주셨군요 ㅜ 정말감사합니다 ! 

    우선 문여는방식을 좀 더 상세히 말하자면  

    학교같은데에 쓰이는겁니다 아마 학교에서 학생들한테만 문을 열게 해주는 그런거같은데요 

    전학생같은경우에도 바로바로 쓸 수 있도록

    인터넷연결을 하지않을까 생각되네요 (바로바로 등록이 되게)


    그리고 리더기에같은경우에는 제가 따로 공부를 더 해봐야할 것 같네요 ㅎㅎ ;; 


    NDEF 방식을 꼭 사용할 필요가 없다니 .. 몰랐네요 

    스마트폰에서 돌아가는거랑 실제리더기에서 돌아가는거랑은 약간 차이가 있나보군요 

    정말 경험에서나오는 팁 감사드립니다


  • ruinnel
    540
    2021-08-04 15:35:01 작성 2021-08-04 15:36:05 수정됨

    NFC 리더기가 들어가는 단말이 인터넷 연결이 있는거군요.


    음... 저라면 NFC 리더기가 들어가 있는 단말이 인터넷 연결이 되어있다고 하더라도..

    실시간으로 인증확인(API 요청해서 succes 받고 문열어주기..)하는 방식으로는 처리 안할거 같습니다.

    그렇게 하면 네트워크 장애가 생기면 문이 아예 안열리게 되거든요.


    각 학생별로 고유값을 부여하고.. 

    앱이 로그인 된 상태에서 리더기에 가져다 대면 고유값을 리더기가 읽어 가고..

    리더기는 주기적으로 문을 열어줘도 되는 고유값 목록을 갱신해서 내부에 저장하고 있다가..

    고유값을 읽어서 내부 저장된 값과 비교해서 열어주는 방식으로 할거 같습니다.



  • 고등어가어딨니
    577
    2021-08-04 15:44:30

    논문읽고왔는데


    리더기가 인터넷통신이 되는 단말기가있고  안되는 단말기도 있다고 하더라고요


    오프라인 단말기 + 태그 명칭이 Off-Off  

    온라인 단말기 + 스마트폰 명칭이 On-On 라고 하네요 ! 

  • 고등어가어딨니
    577
    2021-08-04 15:46:02

    아 선생님 말씀은


    오프라인단말기 와 스마트폰의 조합으로 이루는게 좋다고 하시는거군요 

    확실히 이 방식이 좀 더 효율적이라고 생각이 드네요 

    이건 회사측에서 알아봐야할 것 같습니다 정말 도움 많이됬습니다 ㅜㅜ 정말 감사합니다 !

  • ruinnel
    540
    2021-08-04 16:17:46

    오프라인 단말기 라기보다는..

    온라인 단말기지만 오프라인이 되더라도 기존에 등록된 정보로 문은 열어 줄 수 있는 구성이 실제로 운용했을때 리스크가 훨씬 적을거 같아서 말씀드렸습니다.

  • 고등어가어딨니
    577
    2021-08-04 16:32:57

    아 그런뜻이셨군요 하하 ;;

    이왕이면 오프라인형식의 알고리즘을 사용하는게 안전하겠군요 ! 

    네트워크장애가와도 일처리를 할 수 있게 

    내일 어떤 단말기를 사용할지 나온다니깐 그때가서 확인을 해봐야겠네요


    정말 좋은말씀 감사합니다 ! 

  • 고등어가어딨니
    577
    2021-08-04 16:39:12 작성 2021-08-04 16:42:19 수정됨

    아 그리고 혹시 이 이슈에대해서는 아실런지? 


    제가 지금 앱으로 HCE 상태로 만들었습니다

    그리고 A스마트폰에 그 앱을 설치했고요


    다른 B스마트폰에는 플레이스토어에서 NFC 리더기어플을 다운받았습니다


    그리고 A스마트폰에 설치된 앱 안에

    서비스쪽에

    processCommandApdu 이부분


    이게 의미하는게  리더기에 응답할때 이부분이 자동으로 호출된다는데


    여기에 Log.v("processCommand" , " 리더기발견!")를 붙이고 


    (우선 A와 B둘다 NFC 기본모드로 활성화 한 후)

    서로 앱을 켠상태에서 A 스마트폰과 B스마트폰을 갖다됬는데

    우선 B스마트폰은 플레이스토어에서 가져온 리더기라서 바로 반응은했습니다 
    근데 A 스마트폰에는 (현재 컴퓨터_안드로이드스튜디오와 연결중) Log가 뜨질않았습니다


    이건 A스마트폰에 있는 제가만든앱에 문제가 있는거죠 ?

  • ruinnel
    540
    2021-08-04 17:10:45

    아니요. 만드신 앱의 문제는 아닙니다.

    https://developer.android.com/guide/topics/connectivity/nfc/hce?hl=ko

    요기 보시면. `apduservice.xml`에 `<aid-filter>` 로 값을 지정하게 됩니다.

    그리고  manifest.xml에서 android.nfc.cardemulation.HostApduService를 구현한 서비스에 `<meta-data>`로 apduservice.xml을 지정하게 되구요.


    이 설정이 의미하는게..

    내가 HostApduService를 상속/구현 해서 만든 서비스는 `apduservice.xml`에 `<aid-filter>`에 지정된 값에 대한 통신 요청이 왔을때만 반응하겠다 라는 의미입니다.

    저도 스마트폰쪽을 주로 해서 NFC 통신 아랫단까지 직접 만든건 아니라 이쪽은 대략적인 설명밖에 안되는데...

    NFC 리더기 쪽에서 `aid`가 있는지 물어보는 요청을 하고.. 그 `aid`가 가리키는 서비스와 통신을 하는 그런 절차가 있을거예요.

    AID 라는거 자체가.. Java Card Applet 쪽의 용어인데.. 이쪽까지 가면 복잡할거구요 (저도 이 스펙까지 보진 않았어요)

    여튼.. Java Card 설계에.. 카드내에 applet이 여러개 존재 할수 있고.. 그중 어떤거랑 통신할지 찾는 절차가 있어요.

    실제로 USIM에 들어있는 Tmoney / 캐시비도 applet이고 AID를 가지고 있구요.

    외부에서 NFC리더가 읽는 입장에선 해당 카드에 몇개의 어떤 Applet이 존재하는지 알수 없어요.

    그래서 "이런 aid 가지고 있니?"라고 물어보고 통신을 개시하는 절차가 필요하구요.


    당연히 앱스토어에서 받은 NFC 리더기 어플은 default AID라던가.. 스마트폰에서 쓰는 NDEF 등의 통신을 할때 쓰는 AID를 기본으로 찾거나 할거구요. (이건 어디까지나 저의 추측이고 실제 스펙을 확인한건 아니예요). 

    내가 만든 서비스가 호출 될려면 내가 apduservice.xml에 지정한 aid로 요청을 날려줘야 합니다.


    NFC 라는 규격이 rfid 규격중 13.56MHz 쪽 기술들을 그대로 끌어다가 카테고라이징만 새로하고 위에 공통부문(NDEF 같은거)을 얹은 거구요.

    HCE의 경우... 실제 카드를 에뮬레이션 하는거라 때문에 aid라거나 하는 규격들은 NFC로 추상화되지 않은 그 아래 영역까지 내려가는 부분이 있습니다.

  • 고등어가어딨니
    577
    2021-08-04 17:25:53 작성 2021-08-04 17:28:19 수정됨

    후 .. 그렇군요  한 90퍼정도 이해했습니다

    저도 5일간 나름 공부해서 거의 근접해있는줄 알았는데

    아직 멀었네요 

    그런 경우도 있다는걸 생각자체를 못했네요 


    더 열공을 해봐야겠네요 

    지금까지 문제들은 예제를 (a~z) 확인하면서 풀었는데 

    NFC 호스트기반 카드에뮬레이션은 예제자체가 없으니깐 더욱 어렵게 느껴지네요 


    이렇게된 이상 리더기 자체도 한번 만들어봐야겠네요 

    리더기는 어떻게 AID를 찾는지 잘 모르기에 

    이래야지 돌아가는 원리를 확실히 이해할것같네요 

    답변 정말 감사합니다 ! 


    추가적으로 제가 NFC 태그 (400원짜리) 를 샀는데 

    이것도  스마트폰리더기에 갖다대니깐 읽고 쓰기가 가능한가보네요 

    즉 태그안에도 AID는 아니지만 이런 비슷한 무언가가 있는가봅니다 

  • ruinnel
    540
    2021-08-04 17:36:26 작성 2021-08-04 17:37:37 수정됨

    NFC 리더기 쪽은... 그 분야에서 잘하시는 분이랑 보조 맞춰서 개발했던 터라....

    전 저정도 개념 정도만 잡고.. 실제 리더기쪽에서 맞춰서 개발을 많이 해주셔서... 

    저도 그쪽은 많이 깊이 파진 않았네요 ㅎㅎ.


    Java Card Applet 관련된건 사실.. NFC 리더기 쪽이랑 손 맞춰서 진행하면서 그거까지 알게 된건 아니구요..

    예전에 SKT에서 제휴해서 USIM에다가? 3rd 파티에서 개발한 Applet를 넣을 수 있게 해주는 걸 했었어요.

    (하려다 접었을지도?)

    그때 제휴해서 뭘 해보려고 Java Card Applet 깔짝 깔짝 만들어보고 심사요청해보고 하느라 알게 된 지식이네요.

    (중간에 drop 되었습니다만)


    여튼.. HCE에서 구현하는 HostApduService 가 하는 동작은 사실 이 Java Card Applet 을 구현하는거에 가까운걸로 알고 있습니다.

    실제로 Java card applet 만들때 상속받아서 구현하는 클래스를 보면 더 그런 생각이 들죠..

    https://docs.oracle.com/javacard/3.0.5/api/javacard/framework/Applet.html

    이걸 상속 받아서 구현한 코드가 USIM 같은.. 카드에 들어가는 거죠.

    카드안에 들어가는데 java로 구현하다니... 라는 생각을 했었습니다. ㅋㅋ 근데 그렇다더라구요.




  • 고등어가어딨니
    577
    2021-08-04 17:41:44

    항상 친절한 답변 감사합니다 


    보내주신 링크 참고해보겠습니다 ! 


    정말 대단하십니다 ! (카드안에는 C계열이 들어갈줄알았는데)

  • 로그인을 하시면 댓글을 등록할 수 있습니다.