diff --git a/.github/workflows/ci_gpu.yml b/.github/workflows/ci_gpu.yml index ac2b7e9..d52285c 100644 --- a/.github/workflows/ci_gpu.yml +++ b/.github/workflows/ci_gpu.yml @@ -113,6 +113,7 @@ jobs: run: ./test_gpt2cu build-and-test-llama3: + name: Build and test LLama3.2 1B runs-on: ubicloud-gpu-standard-1-latest env: HF_TOKEN: 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 @@ -150,17 +151,51 @@ jobs: - name: Build BF16 precision run: PRECISION=BF16 make train_llama3cu test_llama3cu + - name: Run default (BF16) + run: ./test_llama3cu + + - name: Run no recompute GeLU (BF16) + run: ./test_llama3cu -r 0 + + - name: Run no master weights (BF16) + run: ./test_llama3cu -w 0 + + - name: Run recompute LN (BF16) + run: ./test_llama3cu -r 2 + + build-and-test-llama3-untied: + name: Build and test LLama3.2 1B with untie weights + runs-on: ubicloud-gpu-standard-1-latest + env: + HF_TOKEN: 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 + steps: + - name: Checkout code + uses: actions/checkout@v4 + - run: echo "::add-mask::$HF_TOKEN" + + - name: Install OpenMP + run: sudo apt-get update && sudo apt-get install -y libomp-dev + + - name: Install dependencies + run: pip install -r requirements.txt + + - name: Run preprocessing + run: python dev/data/tinyshakespeare.py --model_desc llama-3 + + - name: Train model + run: python train_llama3.py --write_tensors 1 --dtype float32 --untie 1 --depth 10 + + - name: Build FP32 precision + run: PRECISION=FP32 make test_llama3cu + - name: Run default run: ./test_llama3cu - - name: Run no recompute GeLU - run: ./test_llama3cu -r 0 + - name: Build BF16 precision + run: PRECISION=BF16 make train_llama3cu test_llama3cu - - name: Run no master weights - run: ./test_llama3cu -w 0 - - - name: Run recompute LN - run: ./test_llama3cu -r 2 + - name: Run default + run: ./test_llama3cu unit-tests-gpu: runs-on: ubicloud-gpu-standard-1-latest diff --git a/train_llama3.py b/train_llama3.py index 04d7ca1..2fc64a6 100644 --- a/train_llama3.py +++ b/train_llama3.py @@ -435,10 +435,16 @@ class LLaMA(nn.Module): return checkpoint @classmethod - def from_pretrained_llama3_hf(cls, model_id): + def from_pretrained_llama3_hf(cls, model_id, untie): """Loads pretrained LLaMA model weights from HuggingFace""" from transformers import AutoModelForCausalLM, AutoTokenizer model_args = MODEL_DICT[model_id] + if untie: + if not model_args.tied_embeddings: + print("Model embeddings are not tied, --untie has no effect.") + else: + print("Untying token embeddings and LM head.") + model_args.tied_embeddings = False model = AutoModelForCausalLM.from_pretrained(model_id) checkpoint = LLaMA.adapt_llama_state_dict_keys_hf(model.state_dict(), model_args) @@ -1040,6 +1046,7 @@ if __name__ == "__main__": parser.add_argument("--output_dir", type=str, default="", help="output directory to which to write logs and checkpoints") parser.add_argument("--model", type=str, default="meta-llama/Llama-3.2-1B", help="chose the llama model") parser.add_argument("--depth", type=int, default=-1, help="load only a subset of the model's layers") + parser.add_argument("--untie", type=int, default=False, help="Untie token embeddings and LM-head, even if they are tied in the checkpoint.") # token layout for each step of the optimization parser.add_argument("--batch_size", type=int, default=4, help="batch size, in units of #batch dimensions") parser.add_argument("--sequence_length", type=int, default=64, help="sequence length") @@ -1144,7 +1151,7 @@ if __name__ == "__main__": # init the model if args.use_hf: - model = LLaMA.from_pretrained_llama3_hf(args.model) + model = LLaMA.from_pretrained_llama3_hf(args.model, args.untie) else: # use Meta's checkpoint assert args.ckpt_dir is not None and os.path.exists(args.ckpt_dir), f"llama3 ckpt dir {args.ckpt_dir} does not exist" assert args.tokenizer_path is not None and os.path.exists(args.tokenizer_path), f"llama3 tokenizer path {args.tokenizer_path} does not exist"