쓰다보니 댓으로 달기엔 너무 긴 것 같아서 글로 씁니다
1. 보여주신 코드를 보면, 아직 개념 안잡힌 분이 보기에는 좀 부적합한 감이 있습니다. 순전히 배우시는 목적으로 보시는 거라면 go의 기본 개념들을 먼저 잡아놓기 위한 다른 좋은 교재, 자료들이 많습니다(tour of go 한국어 버전이나, 노마드코더 무료강의만 쭉 해봐도 하루 이틀 정도면 기본은 어느 정도 잡힙니다. 도서관에서도 Go 관련 책들 찾아보시면 친절한 책들 찾아볼 수 있을 거에요).
2. 그래도 일단 저걸로 올려주셨으니 해석을 해볼게요. 일단 DRMEncoderFile이라는 함수만 해석해 보겠습니다.
한 번에 너무 자세하게 들어가면 헷갈리니까 간략하게 요약해 볼게요. 이 함수는 기본적으로 a랑 b라는 두 개의 인자를 받아서 res라는 결과물을 내보내주고 있습니다. 그 과정에서 이 함수는 크게 이런 과정을 거칩니다.
1) res라는 걸 만듭니다
2) 인자로 받은 a나 b에 이상한 값이 없는지 확인합니다
3) fInPath에 저장되어 있는 경로명으로부터 파일을 읽어들입니다
4) encryptMsg라는 함수를 이용해 읽어들인 정보를 암호화합니다
5) c라는 어레이를 만들어서 암호화된 정보를 여기에 저장합니다
6) fOutPath에 저장되어 있는 경로로 파일을 저장합니다
7) 2~6의 과정중에 에러가 생기면 res에 저장됩니다. 에러가 생기거가 함수가 끝날 시 res를 반환합니다.
3. 그러면 이제 좀 더 세세하게 들어가 볼게요.
func DRMEncoderFile(a TFILEREQUEST, b RKEY) *TFILERESPONSE{
이 함수는 기본적으로 TFILEREQUEST라는 타입으로 a를, RKEY라는 타입으로 b를 인자로 받고 있습니다. 뭐 하는 타입인지는 안 나와있긴 하지만, 뒤에 a.fInPath나 a.fOutPath, b.FID나 b.CEK 등 a랑 b가 각자의 필드를 가지고 있는 걸 보면 구조체라는 걸 알 수 있죠.
함수가 내보내는 TFILERESPONSE도 res.Recode나 res.Result가 있는 걸 보면 구조체입니다. 앞에 *이 붙어서 *TFILERESPONSE라고 되어 있는 건 값을 반환하는 게 아니라 포인터를 반환하기 때문인데요, 포인터에 관해서 설명하면 너무 길어지니까 직접 찾아보시는 게 좋을 것 같네요.
다음으로 넘어가보겠습니다.
1)
res:=어쩌구{}
res.저쩌구
별 거 없습니다. TFILERESPONSE라는 구조체로서 res를 선언하고 필드 값을 정해주는 겁니다.
아마 TFILERESPONSE는 대충 이런 형식의 구조체일 겁니다.
type TFILERESPONSE struct{
Recode string
Result string
...}
구조체 관한 것도 다른 데서 잘 설명된 것들이 많으니 한번 찾아보시고요.
여기서 res라는 게 왜 만들어졌는지는 2)를 보면 대충 짐작할 수 있습니다.
2)
if a.어쩌구==""||....{
res.저쩌구="머시기"
...}
요것도 읽어보면 간단합니다. a라는 구조체에서 fInPath나 fOutPath, 또는 b라는 구조체에서 FID나 CEK가 값이 ""인 경우, 즉 아무것도 없는 필드값이 존재할 경우에는 특정 Recode("6501")와 Result("Input could not 어쩌고~")를 반환해서 어떠한 상황이 발생했는지를 알려주라는 겁니다. 이 경우에 해당하는 경우 &res(res의 포인터 주소)를 반환하면서 함수는 끝이 나고, 빈 값이 없이 정상인 경우 다음 코드로 넘어가게 됩니다.
여기서 ||는 or 논리연산자이고, 자세한 건 if문과 논리연산자 관해서 찾아보시면 됩니다.
그 다음에는 b.FID와 b.CEK를 문자(string)에서 헥스코드(hex)로 변환해서 각각 bFID, bCEK라는 변수에 저장합니다. 이때 ConvStr2Hex라는 함수는 이미 있는 함수가 아니라, 올려주신 코드의 원본 어딘가에 있는 직접 만든 함수일 겁니다.
3)
ReadInfile은 직접 만든 함수일 거여서 뭘 하는지 자세히는 알 수 없습니다.
그래도 생긴 거 보고 추측을 해 보면, 일단 ReadInfile이 a.fInPath에 저장되어 있는 경로로부터 어떤 파일을 읽어오고 있고, 그 결과를 data와 err에 저장하라는 꼴이네요(data에는 실제 정보(또는 메모리 주소), err에는 에러가 발생했는지 여부). 기본적으로 os.Open 함수랑 비슷할 것 같네요.
if err!=nil에서, nil은 값이 존재하지 않을 때를 의미합니다. 에러의 값이 존재하지 않는 게 아닌 경우라면 에러가 있다는 말이겠죠?
go언어에서 에러를 처리하기 위해 정말 많이 쓰이는 말입니다. 외우기 싫어도 코드 조금만 쓰거나 읽다 보면 알아서 외워질 겁니다.
올려주신 코드에서는 에러가 나면 res에 Recode "6502", Result로 err.Error()를 저장하고, res를 반환하고 종료하도록 되어있네요.
4)는 3)이랑 딱히 다를 바 없습니다. encryptMsg가 무슨 함수인지는 안 나와있지만, 암호화 관련 코드니까 CEK는 content encryption key를 의미하는 거일 거고, 아마 특정 키를 받으면 그 키로만 열 수 있게 데이터를 암호화하거나 비슷한 역할을 할 거라고 볼 수 있겠죠. 암호화된 결과는 e에 저장되고요.
에러처리는 3)과 같습니다.
5)에서는 make 함수를 사용해서, e의 길이와 bFID의 길이를 더한 만큼 길이를 가진 바이트 타입의 어레이인 c를 만들어줍니다.
그리고 copy 함수를 사용해서 bFID에 들어있는 내용과 e에 들어있는 내용을 c에다 복사해줍니다.
6)은 5)의 결과인 c를 a.fOutPath에 저장합니다. 에러처리도 위와 같고요.
7)은 그냥 return &res, 즉 함수를 끝내고 &res를 반환하라는 겁니다. 별 건 아니고 그냥 에러 없이 잘 돌아갔는지, 에러가 생겼다면 어떤 에러인지 알려주기 위한 용도입니다.
이 코드를 더 자세히 이해하고 싶으시면
-함수 작성법(func)
-구조체, 배열(struct, array 등의 개념 및 make함수)
-if문(개념&if err!=nil 사용예제, 논리연산자)
-os.Open으로 파일 읽기 예제(위에 코드에서 쓰인 함수는 아니지만 근본은 다 비슷합니다. 혹시 byte나 hex가 뭔지 잘 모르시면 이에 대해서도 간략하게라도 알아두시면 좋습니다)
등에 대해서 공부하시면 좋을 것 같습니다.
그리고 go언어 관한 건 아니지만, contents encrypting key와 key encrypting key에 대해서 알고 계시면 위의 코드가 어떤 목적으로 작성되었는지 이해하시는 데 도움이 될 것 같네요.
ㅎㄷㄷ 정성추 ㅇㅂㅇb
오... 감사합니다 go언어에대한 기본지식이나 언어를 공부하지 않고 바로 과제로 나와버려서 인터넷을 찾으며 시간내로 하려다보니 인터넷이나 책에 나오지 않는건 다른언어에 비해 이해하기나 해석하기 힘든것 같습니다