반응형

아래 링크와 같이 WSL에 설치한 vLLM 서버를 실행하고 사용해 보자.

2026.06.19 - [AI, ML, DL] - [vLLM] WSL 에서 vLLM 설치 및 간단한 실행

 

Background에서 서버를 실행하고 프로세스를 확인.

 

■ 서버 실행하기 (Foreground에서 실행된다)

VLLM_USE_FLASHINFER_SAMPLER=0 python3 -m vllhttp://m.entrypoints.openai.api_server --model LGAI-EXAONE/EXAONE-Deep-2.4B-AWQ --trust_remote_code True --gpu_memory_utilization=0.7

 

■ 서버 실행하기 (Background에서 실행되고 vllm.log 파일에 로그가 기록된다)

VLLM_USE_FLASHINFER_SAMPLER=0 python3 -m vllhttp://m.entrypoints.openai.api_server --model LGAI-EXAONE/EXAONE-Deep-2.4B-AWQ --trust_remote_code True --gpu_memory_utilization=0.7 > vllm.log 2>&1 &

 

VLLM_USE_FLASHINFER_SAMPLER=0은 vLLM이 다음 토큰을 선택(샘플링)할 때 FlashInfer 라이브러리의 고속 커널을 사용하지 않고, PyTorch/Triton 기반의 기본 내장 샘플러를 사용하도록 강제하는 환경 변수 설정이다. 내 시스템에선 이 옵션 없이는 실행할 수 없었다.

 

■ 백그라운드에서 동작중인 서버 프로세스 확인 (백그라운드에서 동작하는 프로세스 중 vllm이라는 문자열과 VLLM이라는 문자열을 검색한다)

ps -ef | grep -E "vllm|VLLM"

 

■ 백그라운드 서버 종료

pkill -f vllhttp://m.entrypoints.openai.api_server

 

 

동작중인 서버를 이용해보자. 아래 코드를 작성하고 실행한다.

from openai import OpenAI

# vLLM 서버 주소 설정 (기본 포트 8000)
client = OpenAI(
    base_url="http://localhost:8000/v1",
    api_key="vllm-token" # api_key는 아무 문자열이나 넣어도 된다.
)

# 단발성 답변 받기 (General Request)
print("=== 일반 답변 요청 ===")
response = client.chat.completions.create(
    model="LGAI-EXAONE/EXAONE-Deep-2.4B-AWQ",  # 동작중인 서버의 모델 이름과 일치해야 한다.
    messages=[
        {"role": "system", "content": "당신은 친절한 AI 도우미입니다."},
        {"role": "user", "content": "인공지능과 거대언어모델(LLM)의 차이점을 한 문장으로 설명해줘."}
    ],
    temperature=0.2,
    top_p=0.95,
    max_tokens=1024
)

print(response.choices[0].message.content)

print()

# 실시간 스트리밍 답변 받기 (Streaming Request)
print("=== 스트리밍 답변 요청 ===")
stream = client.chat.completions.create(
    model="LGAI-EXAONE/EXAONE-Deep-2.4B-AWQ",
    messages=[
        {"role": "system", "content": "당신은 친절한 AI 요리사 도우미 입니다."},
        {"role": "user", "content": "맛있는 김치찌개를 끓이는 비법을 짧게 알려줘."}
    ],
    temperature=0.2,
    top_p=0.95,
    max_tokens=1024,
    stream=True, # 스트리밍 활성화
)

for chunk in stream:
    if chunk.choices[0].delta.content is not None:
        print(chunk.choices[0].delta.content, end="", flush=True)

print()

 

답변 첫 부분에 빈 줄과 </thought> 태그가 따라 나온다.

 

불필요한 태그를 제거해 보자.

from openai import OpenAI

# vLLM 서버 주소 설정 (기본 포트 8000)
client = OpenAI(
    base_url="http://localhost:8000/v1",
    api_key="vllm-token" # api_key는 아무 문자열이나 넣어도 된다.
)

# 단발성 답변 받기 (General Request)
print("=== 일반 답변 요청 ===")
response = client.chat.completions.create(
    model="LGAI-EXAONE/EXAONE-Deep-2.4B-AWQ",  # 동작중인 서버의 모델 이름과 일치해야 한다.
    messages=[
        {"role": "system", "content": "당신은 친절한 AI 도우미입니다."},
        {"role": "user", "content": "인공지능과 거대언어모델(LLM)의 차이점을 한 문장으로 설명해줘."}
    ],
    temperature=0.2,
    top_p=0.95,
    max_tokens=1024
)

#print(response.choices[0].message.content) # 태그 포함 답변 출력
content = response.choices[0].message.content

# </thought> 태그가 포함되어 있다면 분할 처리
if "</thought>" in content:
    # thought_process: 모델이 생각한 과정 (필요시 사용)
    # final_answer: 사용자가 원하는 최종 답변
    thought_process, final_answer = content.split("</thought>", 1)
    #print("=== [AI의 생각 과정] ===")
    #print(thought_process.replace("<thought>", "").strip()) # 시작 태그가 남아있다면 제거
    print(final_answer.strip())
else:
    # 태그가 없는 일반적인 경우 그대로 출력
    print(content)

print()

# 실시간 스트리밍 답변 받기 (Streaming Request)
print("=== 스트리밍 답변 요청 ===")
stream = client.chat.completions.create(
    model="LGAI-EXAONE/EXAONE-Deep-2.4B-AWQ",
    messages=[
        {"role": "system", "content": "당신은 친절한 AI 요리사 도우미 입니다."},
        {"role": "user", "content": "맛있는 김치찌개를 끓이는 비법을 짧게 알려줘."}
    ],
    temperature=0.2,
    top_p=0.95,
    max_tokens=1024,
    stream=True, # 스트리밍 활성화
)

# 실시간 문자열에서 불필요한 </thought> 태그 처리를 위한 변수 선언
full_text = ""
has_passed_thought = False

for chunk in stream:
    if chunk.choices[0].delta.content is not None:
        #print(chunk.choices[0].delta.content, end="", flush=True) # 태그 포함 답변 출력

        token = chunk.choices[0].delta.content
        full_text += token  # 들어오는 토큰을 전체 버퍼에 누적

        # </thought> 태그가 지나갔는지 확인
        if not has_passed_thought:
            if "</thought>" in full_text:
                # 태그가 끝나는 지점을 찾아 그 이후의 텍스트만 추출
                _, final_start_text = full_text.split("</thought>", 1)
                has_passed_thought = True
                
                # 태그 뒤에 공백이나 줄바꿈이 있다면 깔끔하게 지우고 첫 출력
                first_output = final_start_text.lstrip()
                if first_output:
                    print(first_output, end="", flush=True)
            else:
                # 아직 </thought> 태그가 나오기 전(생각 중)이라면 화면에 출력하지 않고 건너뛴다.
                continue
        else:
            # 만약 앞서 출력된 내용이 아직 아무것도 없다면 (sys.stdout이 비어있음)
            # 다음에 들어오는 토큰들도 첫 글자가 나올 때까지 앞쪽 공백/줄바꿈을 계속 지워준다.
            if not full_text.split("</thought>", 1)[1].lstrip():
                # 여전히 공백이나 줄바꿈만 들어오는 상태이므로 출력하지 않고 스킵.
                continue
                
            # 글자가 들어오기 시작하면, 그 시점의 토큰부터 그대로 출력.
            # (단, 공백이 섞여 들어왔을 수 있으므로 첫 진입 토큰만 lstrip 처리)
            if len(full_text.split("</thought>", 1)[1].lstrip()) == len(token):
                print(token.lstrip(), end="", flush=True)
            else:
                print(token, end="", flush=True)

print()

 

불필요한 태그 없이 깔끔하게 정리되었다.

 

 

또한 WSL에 서버를 실행한 상태에서 네이티브 윈도우에서도 위와 동일한 코드로 LLM을 사용할 수 있다.

아니면 WSL에서 hostname -I 명령으로 확인한 IP 주소값을 base_url에 넣어도 된다.

from openai import OpenAI

# vLLM 서버 주소 설정 (기본 포트 8000)
client = OpenAI(
    base_url="http://localhost:8000/v1",
    #base_url="http://172.21.167.101:8000/v1",
    api_key="vllm-token" # api_key는 아무 문자열이나 넣어도 된다.
)

# 단발성 답변 받기 (General Request)
print("=== 일반 답변 요청 ===")
response = client.chat.completions.create(
    model="LGAI-EXAONE/EXAONE-Deep-2.4B-AWQ",  # 동작중인 서버의 모델 이름과 일치해야 한다.
    messages=[
        {"role": "system", "content": "당신은 친절한 AI 도우미입니다."},
        {"role": "user", "content": "인공지능과 거대언어모델(LLM)의 차이점을 한 문장으로 설명해줘."}
    ],
    temperature=0.2,
    top_p=0.95,
    max_tokens=1024
)

print(response.choices[0].message.content)

print()

# 실시간 스트리밍 답변 받기 (Streaming Request)
print("=== 스트리밍 답변 요청 ===")
stream = client.chat.completions.create(
    model="LGAI-EXAONE/EXAONE-Deep-2.4B-AWQ",
    messages=[
        {"role": "system", "content": "당신은 친절한 AI 요리사 도우미 입니다."},
        {"role": "user", "content": "맛있는 김치찌개를 끓이는 비법을 짧게 알려줘."}
    ],
    temperature=0.2,
    top_p=0.95,
    max_tokens=1024,
    stream=True, # 스트리밍 활성화
)

for chunk in stream:
    if chunk.choices[0].delta.content is not None:
        print(chunk.choices[0].delta.content, end="", flush=True)

print()

 

네이티브 윈도우에서 WSL 서버 사용.

 

※ 참고

LG AI Research의 공식 가이드에 따르면 EXAONE Deep 모델은 시스템 프롬프트를 지원하지 않거나 권장하지 않는다. 시스템 프롬프트를 넣으면 모델이 지시사항을 무시하거나 추론(<thought>)을 시작하지 못하고 엉뚱한 답변을 낼 확률이 높아진다. 요리사 같은 페르소나는 아래와 같이 user 메시지 안에 녹여내자.

response = client.chat.completions.create(
    model="LGAI-EXAONE/EXAONE-Deep-2.4B-AWQ",
    messages=[
        # 시스템 프롬프트를 없애고 유저 메시지에 역할을 녹여낸다.
        {"role": "user", "content": "당신은 친절한 AI 도우미입니다. 인공지능과 거대언어모델(LLM)의 차이점을 한 문장으로 설명해줘."}
    ],
    temperature=0.2,
    top_p=0.95,
    max_tokens=1024
)

 

반응형
Posted by J-sean
:
반응형

WSL에서 vLLM을 사용해보자.

 

■ WSL을 설치한다. 운영체제는 우분투 24.04를 설치한다.

우분투 26.04는 파이썬 3.14가 설치되어 있는데 현재 파이토치가 파이썬 3.13까지만 지원하기 때문에 파이토치 설치가 귀찮아진다.

 

■ pip3를 설치한다.

sudo apt update

sudo apt upgrade

sudo apt install python3-pip

pip3 --version (정상 설치 확인)

 

■ 파이썬 가상환경을 만들어 주는 venv를 설치한다.

sudo apt install python3-venv

 

가상환경 생성 및 확인

 

가상환경 활성화

■ venv-vllm 디렉토리에 가상환경을 생성하고 활성화한다.

python3 -m venv venv-vllm

source venv-vllm/bin/activate

 

 

■ 파이토치를 설치한다. (CUDA 12.4)
pip3 install torch torchvision torchaudio --index-url https://download.pytorch.org/whl/cu124

 

vllm을 설치하면 많은 프로그램이 설치된다.

■ vLLM을 설치한다.

pip3 install vllm

 

■ vLLM을 실행하기 위해 CUDA Toolkit을 설치한다. (Cuda Toolkit 12.4)

wget https://developer.download.nvidia.com/compute/cuda/12.4.0/local_installers/cuda_12.4.0_550.54.14_linux.run

sudo sh cuda_12.4.0_550.54.14_linux.run

위 명령을 실행하면 잠시 멈춘 것처럼 시간이 좀 걸린다. 그리고 accept를 입력하고 다음 화면에서 CUDA Toolkit 12.4가 선택된 상태에서 Install을 선택한다. Driver는 옵션에 없었지만 있다면 선택해제한다. Driver를 설치하는 것이 아니다.

 

설치가 끝나면 아래와 같이 환경 변수를 등록한다.

nano ~/.bashrc 실행하고 파일 끝에 아래 내용 추가

export PATH=/usr/local/cuda-12.4/bin${PATH:+:${PATH}}
export LD_LIBRARY_PATH=/usr/local/cuda-12.4/lib64${LD_LIBRARY_PATH:+:${LD_LIBRARY_PATH}}

source ~/.bashrc 실행 (이 명령을 실행하고 나면 파이썬 가상환경이 풀린다)
nvcc --version 명령을 실행하면 버전이 표시된다.

 

 

■ vLLM에서 LGAI EXAON 모델을 사용하는 예

import os

# vLLM에서 FlashInfer 기반의 고속 셈플링(Sampling) 기능을 끄고, 안정적인 PyTorch 네이티브(기본)
# 셈플링 방식으로 되돌리기(Fallback).
os.environ["VLLM_USE_FLASHINFER_SAMPLER"] = "0"
# vLLM은 내부적으로 가속 연산을 위해 FlashInfer라는 라이브러리를 사용하는데 이 라이브러리는
# NVIDIA Turing 아키텍처(Compute Capability sm75) 이상의 GPU에서만 작동한다. 사용하는 그래픽카드가
# 소형 모델 구동용(VRAM 8GB 수준)이면서 sm75보다 낮은 구형 아키텍처(예: GTX 10시리즈인 Pascal 아키텍처 sm61 등)
# 이면 문제가 발생한다.
# 해결 방법: vllm 패키지를 로드하기 전에 os.environ을 통해 FlashInfer 가속 비활성화하기

from vllm import LLM, SamplingParams

def main():
    # 모델 로드
    llm = LLM(
        model="LGAI-EXAONE/EXAONE-Deep-2.4B-AWQ", 
        trust_remote_code=True, 
        gpu_memory_utilization=0.7
    )
# vLLM은 기본적으로 GPU 메모리의 90%(0.9)를 미리 할당하기 때문에, 낮은 성능의 GPU에서는
# OOM(메모리 부족) 에러를 방지하거나 다른 프로세스와 GPU를 나누어 쓰려면 gpu_memory_utilization
# 옵션이 필수적이다.

    # 파라미터 설정
    sampling_params = SamplingParams(
        temperature=0.0,
        top_p=0.95,
        max_tokens=1024,
        repetition_penalty=1.1
    )

    # 질문 리스트
    raw_questions = [
        "대한민국의 수도는 어디인가요?",
        "인공지능은 무엇인가요?"
    ]

    # vLLM 공식 Chat Template 적용
    prompts = []
    tokenizer = llm.get_tokenizer()
    for q in raw_questions:
        messages = [{"role": "user", "content": q}]
        formatted_prompt = tokenizer.apply_chat_template(messages, tokenize=False, add_generation_prompt=True)
        prompts.append(formatted_prompt)

    # 텍스트 생성
    outputs = llm.generate(prompts, sampling_params)

    # 결과 출력 (내장함수로 태그 뒤쪽만 추출)
    for i, output in enumerate(outputs):
        prompt = raw_questions[i]
        # output.prompt로 프롬프트를 추출할 수도 있지만 불필요한 태그가 많이 따라온다. 정제과정이 필요.
        generated_text = output.outputs[0].text
        
        # </thought> 태그가 존재한다면 그 태그 뒷부분([1])만 추출한다
        if "</thought>" in generated_text:
            clean_answer = generated_text.split("</thought>")[1]
        else:
            clean_answer = generated_text

        print(f"==========================================")
        print(f"질문: {prompt}")
        print(f"답변: {clean_answer.strip()}")
        print(f"==========================================\n")

if __name__ == "__main__":
    main()

 

EXAON 모델이 다운로드되어 있지 않다면 다운로드하느라 이 화면에서 시간이 좀 걸린다.

위 코드에서는 토큰 없이 허가되지 않은 접근을 하고 있기 때문에 다운로드가 느리다고 한다. 토큰을 받고 빠르게 다운로드하는 방법은 맨 아래 내용을 참고하자.

 

최종 결과 화면

 

 

다시 실행하면 모델을 다운로드하는 과정이 없다.

 

import os
os.environ["VLLM_USE_FLASHINFER_SAMPLER"] = "0"

from vllm import LLM, SamplingParams

def main():
    llm = LLM(
        model="LGAI-EXAONE/EXAONE-Deep-2.4B-AWQ", 
        trust_remote_code=True, 
        gpu_memory_utilization=0.7
    )

    sampling_params = SamplingParams(
        temperature=0.0,
        top_p=0.95,
        max_tokens=1024,
        repetition_penalty=1.1
    )

    raw_questions = [
        "대한민국의 수도는 어디인가요?",
        "인공지능에 대해 한 문장으로 요약해줘."
    ]

    prompts = []
    tokenizer = llm.get_tokenizer()
    for q in raw_questions:
        messages = [{"role": "user", "content": q}]
        formatted_prompt = tokenizer.apply_chat_template(messages, tokenize=False, add_generation_prompt=True)
        prompts.append(formatted_prompt)

    outputs = llm.generate(prompts, sampling_params)

    for i, output in enumerate(outputs):
        prompt = raw_questions[i]
        generated_text = output.outputs[0].text
        
        if "</thought>" in generated_text:
            clean_answer = generated_text.split("</thought>")[1]
        else:
            clean_answer = generated_text

        print(f"==========================================")
        print(f"질문: {prompt}")
        print(f"답변: {clean_answer.strip()}")
        print(f"==========================================\n")

    print(outputs)

if __name__ == "__main__":
    main()

 

짧은 답변이 나오도록 질문을 바꾸고 전체 결과가 출력되도록 print(outputs) 명령을 추가했다.

 

마지막에 outputs의 내용이 출력되었다.

 

[RequestOutput(request_id=0, prompt='[|system|][|endofturn|]\n[|user|]대한민국의 수도는 어디인가요?\n[|assistant|]<thought>\n', prompt_token_ids=[420, 453, 47982, 453, 422, 361, 560, 420, 453, 14719, 453, 422, 36437, 730, 8952, 657, 4083, 798, 7799, 392, 560, 420, 453, 1167, 8659, 453, 422, 389, 52040, 391, 560], encoder_prompt=None, encoder_prompt_token_ids=None, prompt_logprobs=None, outputs=[CompletionOutput(index=0, text='\n</thought>\n\n 대한민국의 수도는 서울(Seoul)입니다.', token_ids=[560, 2240, 52040, 391, 560, 560, 9971, 730, 8952, 657, 2879, 369, 8078, 10103, 370, 10996, 375, 361], routed_experts=None, cumulative_logprob=None, logprobs=None, finish_reason=stop, stop_reason=None)], finished=True, metrics=None, lora_request=None, num_cached_tokens=0), RequestOutput(request_id=1, prompt='[|system|][|endofturn|]\n[|user|]인공지능에 대해 한 문장으로 요약해줘.\n[|assistant|]<thought>\n', prompt_token_ids=[420, 453, 47982, 453, 422, 361, 560, 420, 453, 14719, 453, 422, 41595, 22427, 2373, 2409, 764, 13742, 13456, 16399, 999, 15887, 375, 560, 420, 453, 1167, 8659, 453, 422, 389, 52040, 391, 560], encoder_prompt=None, encoder_prompt_token_ids=None, prompt_logprobs=None, outputs=[CompletionOutput(index=0, text='\n</thought>\n\n인간의 intelligence를 computer로 구현하는 것.', token_ids=[560, 2240, 52040, 391, 560, 560, 25284, 730, 13887, 4605, 6458, 715, 19495, 1130, 657, 924, 375, 361], routed_experts=None, cumulative_logprob=None, logprobs=None, finish_reason=stop, stop_reason=None)], finished=True, metrics=None, lora_request=None, num_cached_tokens=0)]

 

 

그런데 이렇게 진행하는 모델은 내부에 config.json 파일이 있어야 한다. (정확히는 gguf 포맷의 모델은 바로 사용할 수 없다는 것이다)

예를 들어 EXAON은 config.json 파일이 있지만 Bllossom-3B-gguf-Q4_k_M은 없다. 그래서 Bllossom-3B-gguf-Q4_k_M은 vLLM에서 바로 사용할 수 없다. (아래 참고 1~2를 참고한다)

 

config.json 파일이 없다. (gguf 포맷 모델이므로)

 

config.json 파일이 없다는 에러가 발생한다.

 

config.json 파일이 있다.

 

config.json 파일이 있다.

 

 

※ 참고 1

■ Hugging Face에서 (Bllossom-3B-gguf-Q4_K_M) 모델 다운로드하기

hf 명령어를 사용한다. huggingface-cli는 더 이상 사용하지 않는다. 위 과정을 진행했다면 hf(Hugging Face Hub CLI)는 이미 설치되어 있다.

파이썬 가상화 환경을 시작한다.

hf auth login
Paste an access token 옵션을 선택하고 Profile - Settings - Access Tokens에서 생성한 토큰을 붙여넣는다.
로그인이 완료된다.

로그인 확인하기
hf auth whoami

Bllossom-3B-gguf-Q4_K_M 모델 다운로드하기
hf download Bllossom/llama-3.2-Korean-Bllossom-3B-gguf-Q4_K_M
로그인하지 않은 상태에서 다운로드하면 느리게 진행되지만 로그인을 했으므로 빠르게 진행된다.

모델 다운로드 위치
/home/sean/.cache/huggingface/hub/
예) /home/sean/.cache/huggingface/hub/models--Bllossom--llama-3.2-Korean-Bllossom-3B-gguf-Q4

 

※ 참고 2

Bllossom-3B-gguf-Q4_K_M 같은 gguf 포맷 모델 저장소에는 config.json 파일이 포함되어 있지 않다. guff 파일은 모델의 가중치뿐만 아니라 토크나이저 설정, 레이어 수, 아키텍처 정보 등 config.json에 들어가는 모든 메타데이터를 단일 guff 파일 내부에 바이너리 형태로 통합하여 저장하기 때문이다. 모델의 메타데이터와 아키텍처 구조를 확인하거나 다른 라이브러리와 호환을 맞추기 위해 json 파일이 필요하다면 양자화되기 전 원본 모델 저장소인 Bllossom/llama-3.2-Korean-Bllossom-3B에 있는 config.json 및 토크나이저 설정 파일들을 사용하면 된다. (설정 파일을 직접 다운로드 받아 gguf 파일이 있는곳에 저장할 필요는 없다)

 

llm = LLM(
        model="/home/sean/.cache/huggingface/hub/models--Bllossom--llama-3.2-Korean-Bllossom-3B-gguf-Q4_K_M/snapshots/c07b7a0f2688d1212612b653a752a0dfe4e18bae/llama-3.2-Korean-Bllossom-3B-gguf-Q4_K_M.gguf",
        # 모델은 저장된 경로와 이름을 정확히 적어준다.
        tokenizer="Bllossom/llama-3.2-Korean-Bllossom-3B",
        # 토크나이저는 저장소 이름을 적어줘도 된다.
        trust_remote_code=True,
        gpu_memory_utilization=0.7,
        dtype="float16",
    )

하지만 위와 같이 LLM 클래스를 생성하면 될 것 같은데, WSL에서 실행하면 계속 UVA 관련 에러가 발생한다. WSL이 아닌 리눅스를 네이티브 운영체제로 사용하는 환경에서 테스트해 봐야 할 것 같다.

 

또한 vLLM에서 gguf 포맷 모델 사용은 실험적 단계이며 특별한 제약과 조건이 있어 추천하지 않는다. vLLM은 AWQ, GPTQ, FP8 같은 GPU 네이티브 양자화 포맷에서 제대로 된 성능이 나온다. gguf 포맷 모델을 로컬 환경에서 편하고 안정적으로 사용하려면 Ollama를 사용하자.

 

GGUF(GPT-Generated Unified Format)는 인공지능 모델(특히 LLM)을 개인 PC나 노트북 같은 로컬 환경에서 빠르고 효율적으로 실행하기 위해 설계된 단일 파일 모델 포맷이다.

3B: 모델의 매개변수가 30억 개이다. (3 Billion)

Q4: 4비트 양자화를 의미. 원래 16비트인 모델을 4비트로 압축하여 파일 용량과 메모리를 1/4로 줄였다는 뜻.

K_M: 양자화 기법의 종류. 보통 _L(Large), _M(Medium), _S(Small) 로 나뉘며, Q4_K_M은 성능 저하를 최소화하면서 용량을 줄인 가장 대중적이고 밸런스가 좋은 기법이다.

 

■ UVA

WSL에서 UVA는 일반적으로 엔비디아(NVIDIA)의 Unified Virtual Addressing(통합 가상 주소) 기술을 의미합니다.
이는 GPU가 컴퓨터 메모리(RAM)와 GPU 자체 메모리를 하나의 주소 공간으로 다룰 수 있게 해주는 기술입니다. WSL 환경에서는 AI/머신러닝(예: PyTorch)을 구동할 때 GPU 가속을 위해 필수적으로 사용되는 핵심 기능입니다.

WSL에서 UVA가 중요한 이유
1. 메모리 접근 단순화: CPU 메모리와 GPU 메모리 간의 데이터를 복사할 때 위치를 일일이 지정할 필요가 없습니다.
2. AI 및 딥러닝 가속: vLLM이나 대형 모델(LLM) 학습 시 VRAM 부족을 해결하기 위해 CPU RAM을 공유해 사용할 때(CPU Offloading), 이 기술이 필수적으로 작동해야 합니다.
3. 호환성 이슈 해결: 종종 WSL 환경에서 이 기능이 제대로 감지되지 않으면 메모리 오류가 발생하거나 가속 기능이 작동하지 않을 수 있습니다.

 

 

 

※ 참고 3

파일 익스플로러 주소창에 \\wsl$를 입력하면 WSL에 설치된 운영체제의 파일에 접근할 수 있다. 물론 왼쪽 패널에 Linux - Ubuntu-24.04로 접근해도 된다.

 

※ 참고 4

vLLM Documentation

vLLM GitHub

 

반응형
Posted by J-sean
: