LoginSignup
1
2

More than 5 years have passed since last update.

Cソースコードを Clang と vscode for mac で デバッグ

Last updated at Posted at 2019-02-09

Cソースコードを Clang と vscode for mac で デバッグ

repos: https://github.com/sato1043/try_clang_env

概要

  • C言語環境のキャッチアップ実施。
  • 手持ちの Mac が XCode 導入済で、 Clang を利用
  • vscode for mac で IDEデバッグ

準備

  • XCode
  • homebrew
  • vscode
$ brew cask install visual-studio-code
  • Cmd + Space -> visual studio code
  • vscode上で) F1 -> install extensions

  • vscode上で) F1 -> configure default build task

{
    // See https://go.microsoft.com/fwlink/?LinkId=733558
    // for the documentation about the tasks.json format
    "version": "2.0.0",
    "tasks": [
        {
            "label": "make",
            "type": "shell",
            "command": "make",
            "args": ["-j4", "debug"],
            "group": {
                "kind": "build",
                "isDefault": true
            }
        }
    ]
}
  • ccache
$ brew install ccache
$ echo 'export PATH=/usr/local/opt/ccache/libexec:$PATH' >> ~/.profile
 # => .profile は自分のシェル用のprofile
  • clang-format
$ brew install clang-format
$ clang-format -dump-config -style=Google > .clang-format
  • vscode上で) F1 -> install extensions
  • vscode上で) F1 -> open settings(JSON)
{
    "editor.formatOnSave": true
}
  • cppcheck
  • cunit
  • tcmalloc(gperftools)
  • valgrind
$ brew install cppcheck cunit gperftools valgrind
  • vscode上で) F1 -> install extensions
  • global
$ xcode-select --install
$ brew install global
  • vscode上で) F1 -> open settings(JSON)
{
     :
    "codegnuglobal.executable": "/usr/local/bin/global"
}
  • vscode上で) F1 -> install extensions
$ brew install plantuml

コード

Makefile

  • vscode上で) F1 -> new file
  • ファイル名は Makefile

TARGET := a.out

MAIN_C := ./main.c
TEST_C := ./test.c
SRCS := $(filter-out $(TEST_C), $(wildcard ./*.c) $(wildcard ./**/*.c))
OBJS := $(SRCS:%.c=%.o)
DEPS := $(SRCS:%.c=%.d)
-include $(DEPS)

TSRCS := $(filter-out $(MAIN_C), $(wildcard ./*.c) $(wildcard ./**/*.c))
TOBJS := $(TSRCS:%.c=%.o)
TDEPS := $(TSRCS:%.c=%.d)
-include $(TDEPS)

.PHONY: release debug all check clean test

CFLAGS := -std=c17 -Weverything
CFLAGS_D :=-O0 -DDEBUG -g
CFLAGS_R :=-O2 -DNDEBUG

LDFLAGS :=-ltcmalloc
LDFLAGS_D :=-g -debug
LDFLAGS_R :=

all: CFLAGS+=$(CFLAGS_R)
all: LDFLAGS+=$(LDFLAGS_R)
all: clean $(TARGET)

debug: CFLAGS+=$(CFLAGS_D)
debug: LDFLAGS+=$(LDFLAGS_D)
debug: check $(TARGET)

CC := clang

.c.o:
    $(CC) -MMD -MP $(CFLAGS) -c $<

$(TARGET): $(OBJS)
    $(CC) $(LDFLAGS) -o $(TARGET) $(OBJS)

run: $(TARGET)
    valgrind --leak-check=full ./$(TARGET)

time: $(TARGET)
    time ./$(TARGET)

test: $(TARGET).cunit
    valgrind --leak-check=full ./$(TARGET).cunit

$(TARGET).cunit: $(TOBJS)
    $(CC) $(LDFLAGS) -lcunit -o $(TARGET).cunit $(TOBJS)

dSYM: $(TARGET)
    dsymutil $(TARGET)

tags:
    gtags -v

check:
    @for src in $(SRCS) ; do \
        clang-format -i "$$src" ; \
        cppcheck --enable=all --check-config "$$src" ; \
    done

clean:
    -rm -rf $(DEPS) $(OBJS) $(TDEPS) $(TOBJS) $(TARGET) $(TARGET).dSYM $(TARGET).cunit $(TARGET).cunit.dSYM

usecase.puml

@startuml
User -> (Start)
@enduml

main.c

  • vscode上で) F1 -> new file
  • ファイル名は main.c
#include <stdio.h>

#include "functions.h"

int main(int argc, char **argv) {
  say_hello();
}

functions.h

  • vscode上で) F1 -> new file
  • ファイル名は functions.h
#pragma once
int say_hello(void);

functions.c

  • vscode上で) F1 -> new file
  • ファイル名は functions.c
#include <stdio.h>

#include "functions.h"

int say_hello() {
  printf("hello world\n");
  return 0;
}

test.c

  • vscode上で) F1 -> new file
  • ファイル名は test.c
#include "CUnit/Basic.h"
#include "CUnit/CUnit.h"

#include "functions.h"

void test_say_hello(void);

int main(void) {
  CU_pSuite testSuite;

  CU_initialize_registry();

  testSuite = CU_add_suite("ATestSuite", NULL, NULL);

  CU_add_test(testSuite, "test_say_hello", test_say_hello);

  CU_basic_set_mode(CU_BRM_VERBOSE);
  CU_basic_run_tests();

  CU_cleanup_registry();

  return 0;
}

void test_say_hello(void) { CU_ASSERT(say_hello() == 0); }

a.out.cunit

  • vscode上で) F1 -> new terminal
$ make test
  :
./a.out.cunit


     CUnit - A unit testing framework for C - Version 2.1-3
     http://cunit.sourceforge.net/


Suite: ATestSuite
  Test: test_say_hello ...hello world
passed

Run Summary:    Type  Total    Ran Passed Failed Inactive
              suites      1      1    n/a      0        0
               tests      1      1      1      0        0
             asserts      1      1      1      0      n/a

Elapsed time =    0.000 seconds

a.out

  • vscode上で) F1 -> run build
  • vscode上で) F1 -> new terminal
$ ./a.out
hello world

デバッグ

  • vscode上で) F1 -> start debugging
    • 初回、設定の新規作成を促される。
    • "C++(gdb/lldb)"を選択してlaunch.json編集
{
    // Use IntelliSense to learn about possible attributes.
    // Hover to view descriptions of existing attributes.
    // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
    "version": "0.2.0",
    "configurations": [
        {
            "name": "(lldb) Launch",
            "type": "cppdbg",
            "request": "launch",
            "program": "${workspaceFolder}/a.out", <==ここ
            "args": [],
            "stopAtEntry": true, <==ここ
            "cwd": "${workspaceFolder}",
            "environment": [],
            "externalConsole": false, <==ここ
            "MIMode": "lldb"
        }
    ]
}
  • F5
    • main関数冒頭でブレイク。できました。
1
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
2