퇴근5분전

 

올라마( 라마3.1, 라마3.2 ) + 시멘틱 커널(c#) 조합으로 로컬 AI를 구성하고 

몇일 가지고 놀아봤는데... 

 

프롬프트가 개짜증나네...ㅡ.,ㅡ;;;

 

MSI 노트북 4060( 8GB )으로 돌리는데... 

파워쉘:

 ollama ps  

결과 :: 사용하는 자원이 뭔지 보여준다. 처음엔 CPU 100% 떴는데... 설정 바꾸고 GPU100%가 뜬다.

 

처음엔 GPU타는줄 알고 있다가 작업관리자로 GPU0(내장), GPU1(외장)을 보니 내장? 그리고 CPU로 동작하는 것을 보고

드라이버도 업데이트하고 

시스템 > 디스플레이 > 그래픽

       > 앱추가 로 올라마, 올라마서버, 올라마 앱을 등록해놓고 

       > 각 앱별로 GPU 기본 설정을 "고성능(NVIDIA Geforce RTX 4060 Laptop GUP)"

       > 설정 후 재부팅. 

 

이후로 GPU가 동작하는 것을 보고. 프롬프트를 이리 저리 바꿔보는데...

로컬AI라서 그런지??? 크롬-제미나이, 엣지-코파일럿 에 동일한 질의문을 던졌을때와는 결과 값을 받는게 너무 다르다. 

  다른점! 제미나이, 코파일럿은 일정하게 앞에 붙는 문구들을 제약하면 제대로 값이 나온다. 

       이 라마3.1이나 3.2는 제약을 해도 쌩까고 붙여준다. 

       예시) "결과: 30" 이 나오는데 "결과:" 붙이지 말라고 해도 붙어서 온다.

 

이상한 설명이 붙거나, 하지 말라고 지시문에 넣어도 "결과:" 이게 붙네?... 

이렇게 되면 로컬AI에서 받은 답변을 또 뭔가 바꾸고 해야 하는데...

 

-----------

llama3.2 로 지정하면 GPU 전용 메모리 2.5GB가 할당되는걸 볼 수 있다. 

llama3.1 로 지정하면 GPU 전용 메모리 4.5GB가 할당되는걸 볼 수 있다.

 

시멘틱커널로 호출할때 지정할 수 있는데... 바꾸면 메모리 바뀌는 것도 보이는데...

 

프롬프트가 각 버전마다 좀 달라져야 하는 것 같다. 

동일한 프롬프트로 버전만 바꾸면 적용이 안된다. 

프롬프트를 잘 못 작성해서 그런가? 이거 쉽지 않네.

 

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

프롬프트 인식을 제대로 못해서 gemma2:9b-instruct-q4_K_M으로 모델을 바꿨다.

대신 플러그인 기능을 사용할 수 없으니... 프롬프트에 데이타를 묶어서 던지는 것으로 바꾼다.

 llama3.1, llama3.2는 

"10, 20, 30 중 15보다 큰 것들을 보여줘." 라고 보내면

온갖 문구들을 가져다 붙인다. 그래서 temperature=0 으로 보냈는데도 붙인다. 

미사여구, 설명, 친절하지 말라등등.. 다 붙여봤는데... 소용없다. 

그리고 10, 20, 30을 결과로 줄때도 있었다. 

이걸 올라마 콘솔에서 해보면 제대로 준다. 시멘틱커널에서 보낼때 뭔가 작용하는 듯 하고... 

 

모델을 바꾸고 해보면 gpu전용메모리에 6GB를 점유한다. 

'속담까지는 모르네...' 

 

  플젝 끝내고 지난 일주일간 코파일럿, 제미나이로 검색을 통해 로컬AI로 할 수 있는게 뭘까를 

계속 찾아봤다.  여러가지 케이스를 정의하고 써먹을 곳을 찾았고...

 

 오늘 그 시작을 했다. 

노트북[ 올라마 설치, llama3.2설치] :: 외장그래픽카드 4060 ( 8GB )

데스크탑PC[VS에서 윈폼프로젝트(Net 8.0) 생성, 시멘틱커널 사용하는 누겟 설치 ]

그리고 테스트 코드를 두개 만들었다. 

 

1. "A:10, B:20, C30에서 15보다 큰 것을 찾아줘" 이런 프롬프트로 올라마에 던져서 

데스크탑과 노트북에서 데이타 주고 받고 잘 하는지 봤고,

 

2. 시멘틱커널에 플러그인을 생성해서 두 숫자를 더하는 메소드가 요청 처리에 호출되는지 확인했다. 

 

위 두개 모두 성공했다. 

 

 로컬AI인 만큼 로컬에서 데이타를 제공하고 AI가 나머지 처리를 하도록 프롬프트를 작성 잘 하는건데...

이때 필요한 데이타는 플러그인이나 프롬프트에 추가해서 제공하는 것으로 그 방향성을 잡았다. 

 

이렇게 하면 할 수 있는 일들이 많다. 반복적인 일들을 플러그인을 추가하면서 AI에 맡길 수 있고.

네트웍 내부 망에서 데이타를 가져다 AI에 제공도 가능하고... VRAM이 커야 좀 더 큰 모델을 쓸 수 있겠지만... 

그거야 나중에 그래픽카드를 좋은거 쓰든가.. ai용 머신을 사든가... 등등... 

 

 일단 생각하는데로 ai를 굴릴수 있는지 확인하는 것이 먼저라서...

마지막 프로젝트가 설비관련 MES의 DAT였으니까... 그와 관련된 몇가지 케이스를 적어놨는데... 

흉내만 내볼 예정이다. 

 

 위 간단한 10 + 30을 플러그인으로 처리 요청을 보냈더니 5~7초 걸리더라... 

한번 구성해두면 매번 같은 일 안해도 될 것 같은 생각에 구조에 신경써보자. 

 

 

 

 

 

 

 일단 프로젝트가 저번주에 끝났다. 

 

Tcp/Ip 통신으로 PLC와 통신하여 값들을 읽어서 설비동작에 응답하고, DB저장하는 처리를 하였는데... 

 

랜선 뽑기.. 대응이 잘 안되더라.

 

설비에서 진동? 같은걸로 통신중에 랜선이 망가지거나... PLC가 동작을 안해서라든가... 통신카드가 고장났다던가... 

라는 상황에 대비해 랜선을 뽑아보는 테스트를 했는데...

반응이 느리다.. 20초 걸리고 스탑되니까... 

 

 월화 이틀간 여러 테스트를 직접 해보고 찾아봤는데... tcpip는 좀 다르긴 하다. 

보통 뭔가 사용하기전 체크를 먼저 다 마치고 사용을 하는 구조로 작업을 하는데... 

tcpip는 우선 던지고 예외가 발생하면 끊김여부를 확인 할 수 있어서... 

이런 식으로 코드를 변경해서 샘플 테스트를 마쳤다. 새로 만든 통신 코드는 잘 되는데, 다른 문제가 생겼네? 

 

C#을 주력언어로 사용하는 나는 옛날꼰날부터 비동기 코드하면

대리자.BeginInvoke... 를 이용해서 비동기 코드를 작성해왔다. 

PLC 프로그램 하면서 Task를 써보기로 하고, Task.Run 을 이용해서 비동기 코드를 작성했었고.. 

async, await는 그렇게 자주 사용하는 코드는 아니었는데... 

이번 일 끝나고 좀 더 깊이 공부를 했다. 이유는 LS 산전 PLC 통신 프로토콜을 이용해서 통신하는데 

기존 구현되어 있던 코드가 이상괴팍해서리... 새로 만들어줄까 싶어서 조금 변경했더니... 

 패킷이 꼬이더라... 이유는 PLC에 주소값 요청을 날리고 바로 수신하면 그 응답이 오는 구조인데...

백그라운드 워커가 25개정도 돌아가는데 각 워커에서 요청 응답을 날리니까 이게 하나만 꼬여도

응답이 제대로 안넘어오고 섞이는게 생기더라. ( 희안한 경험이었다. )

 그래서 LS 통신 프로토콜 스팩이랑 코파일럿 AI등으로 검색등을 해보니.. 패킷중에 InvokeID라는 필드값이 있었다. 

요청에 InvokeID를 보내면 응답으로 InokeID가 오는 것으로 이것으로 구분이 가능했다. 

 이거 저거 체크하면서 구조를 콜백구조로 바꾸고 InvokeID로 대응시켜서 처리하다보니 Task를 써서 잘 만들어보고 싶어서 ... 

Task를 좀 더 봤다. 

 

async Task MethodName( )

{

         await Task.Delay(100);

}

 이렇게 작성된 것 차체만으로도 비동기적으로 돌아가는걸 이제 알았다. 헐!...

 새로 만든다면 이런 구조가 필요한 곳들이 많았는데... Task.Run안쓰고 위 구조로 하면 굳이 쓰레드를 따로 할당받고 복귀하고 할 필요가 없다는 것도 AI의 답변이고... 

 

 게다가 위처럼 만들면 UI 컨트롤에 값 설정할때 굳이 Invoke 안해도 되고... 

또 하나 공부를 마쳤다. 새로 만드는 기회가 있다면 좀 더 코드가 정리 될 것 같다.