0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

WebAssembly で Awk を実行する

Last updated at Posted at 2025-10-24

One True Awk

これまでの記事 で自作プログラムを動かすことができるようになったので、OSS のプログラムを移植してみる。

ネットワークやデバイスが関連するものは難しいと思うので、テキスト処理をするものとして One True Awk を選択した。

本来は makefile を移植するのがセオリーかもしれないが、ビルドに bison が必要だったり、maketab.c をコンパイルしたものをツールとして使っていたりするので、Windows の環境で実現するのには手間がかかる。

そこで Ubuntu Linux を使って 公式の資料 に従い、以下のように生成したソース・ファイルを Windows に配置した。

ubuntu@vm1:~$  git clone https://github.com/onetrueawk/awk.git
Cloning into 'awk'...
remote: Enumerating objects: 2335, done.
remote: Counting objects: 100% (673/673), done.
remote: Compressing objects: 100% (211/211), done.
remote: Total 2335 (delta 524), reused 462 (delta 462), pack-reused 1662 (from 2)
Receiving objects: 100% (2335/2335), 4.12 MiB | 6.11 MiB/s, done.
Resolving deltas: 100% (1365/1365), done.
ubuntu@vm1:~$ cd awk
ubuntu@vm1:~/awk$ make
bison -d  awkgram.y
awkgram.y: warning: 44 shift/reduce conflicts [-Wconflicts-sr]
awkgram.y: warning: 85 reduce/reduce conflicts [-Wconflicts-rr]
awkgram.y: note: rerun with option '-Wcounterexamples' to generate conflict counterexamples
cc -g -Wall -pedantic -Wcast-qual   -O2   -c -o awkgram.tab.o awkgram.tab.c
cc -g -Wall -pedantic -Wcast-qual   -O2   -c -o b.o b.c
cc -g -Wall -pedantic -Wcast-qual   -O2   -c -o main.o main.c
cc -g -Wall -pedantic -Wcast-qual   -O2   -c -o parse.o parse.c
cc -g -Wall -pedantic -Wcast-qual -O2 maketab.c -o maketab
./maketab awkgram.tab.h >proctab.c
cc -g -Wall -pedantic -Wcast-qual   -O2   -c -o proctab.o proctab.c
cc -g -Wall -pedantic -Wcast-qual   -O2   -c -o tran.o tran.c
cc -g -Wall -pedantic -Wcast-qual   -O2   -c -o lib.o lib.c
cc -g -Wall -pedantic -Wcast-qual   -O2   -c -o run.o run.c
cc -g -Wall -pedantic -Wcast-qual   -O2   -c -o lex.o lex.c
cc -g -Wall -pedantic -Wcast-qual   -O2 awkgram.tab.o b.o main.o parse.o proctab.o tran.o lib.o run.o lex.o   -lm

以下のうち maketab.c 以外が Awk のソースコードとなる。

ubuntu@vm1:~/awk$ ls *.c *.h
awk.h          awkgram.tab.h  lex.c  main.c     parse.c    proto.h  tran.c
awkgram.tab.c  b.c            lib.c  maketab.c  proctab.c  run.c

また、入力ファイルは適当に検索して見つかった address-sample.csv を利用している。

ubuntu@vm1:~/awk$ curl -sSLO https://raw.githubusercontent.com/geocommons/geocoder/refs/heads/master/test/data/address-sample.csv
ubuntu@vm1:~/awk$ ./a.out --csv 'NR!=1 {print $14,$11,$12;} NR>5 {exit;}' address-sample.csv
11211  Brooklyn
02903  Providence
03561  Littleton
04401  Bangor
04901  Waterville

ファイル一覧

VSCode の CMake プロジェクトを構成するファイルの一覧は以下の通り。

C:\wasm\project\16-awk.vscode\launch.json
{
    "version": "0.2.0",
    "configurations": [

        {
            "type": "chrome",
            "request": "launch",
            "name": "localhost:8080",
            "url": "http://localhost:8080/",
        }
    ]
}

cacheVariables にあった CXX 系のものは削除

C:\wasm\project\16-awk\CMakePresets.json
{
  "version": 5,
  "cmakeMinimumRequired": {
    "major": 3,
    "minor": 20,
    "patch": 0
  },
  "configurePresets": [
    {
      "name": "wasm-config",
      "hidden": true,
      "generator": "Ninja Multi-Config",
      "binaryDir": "${sourceDir}/build",
      "cacheVariables": {
        "CMAKE_TOOLCHAIN_FILE": "$env{EMSDK}/upstream/emscripten/cmake/Modules/Platform/Emscripten.cmake",
        "CMAKE_EXPORT_COMPILE_COMMANDS": "ON",
        "CMAKE_CONFIGURATION_TYPES": "Debug;Release"
      }
    },
    {
      "name": "wasm-config-debug",
      "inherits": "wasm-config",
      "cacheVariables": {
      }
    },
    {
      "name": "wasm-config-release",
      "inherits": "wasm-config",
      "cacheVariables": {
      }
    }
  ],
  "buildPresets": [
    {
      "name": "wasm-build-debug",
      "configurePreset": "wasm-config-debug",
      "verbose": true,
      "configuration": "Debug"
    },
    {
      "name": "wasm-build-release",
      "configurePreset": "wasm-config-release",
      "verbose": true,
      "configuration": "Release"
    }
  ]
}
  • project(LANGUAGES) では C言語 を指定している
  • file(GLOB) により awk/ ディレクトリ以下の *.c をソースファイルとする
  • --preload-file を使って、入力ファイルを仮想ファイルシステムの /address-sample.csv として配置
C:\wasm\project\16-awk\CMakeLists.txt
cmake_minimum_required(VERSION 3.20)
project(16_awk LANGUAGES C)

file(GLOB SOURCES "awk/*.c")
add_executable(16_awk ${SOURCES})

target_link_options(16_awk PRIVATE
    $<$<CONFIG:Debug>:-gsource-map -sASSERTIONS=1 -sSAFE_HEAP=1>
    "-sEXPORT_ES6=1"
    # https://github.com/geocommons/geocoder/blob/master/test/data/address-sample.csv
    "--preload-file=${CMAKE_SOURCE_DIR}/address-sample.csv@address-sample.csv"
)
  • awk の main() 関数の引数に「--csv NR!=1 ...」を指定
C:\wasm\project\16-awk\index.html
<!DOCTYPE html>
<html lang="ja">
    <head>
        <meta charset="utf-8"/>
        <script type="module">
            import Module from './build/Debug/16_awk.js';

            const locateFile = (path, prefix) => {
                console.log(`locateFile(path=${path}, prefix=${prefix})`)

                if (path.endsWith(".data")) {
                    return './build/Debug/' + path;
                }

                return prefix + path;
            };

            const preRun = [
                emsModule => { console.log('# AWK-START'); },
            ];

            const postRun = [
                emsModule => { console.log('# DONE.'); },
            ];

            const args = [
                '--csv',
                'NR!=1 {print $14,$11,$12;} NR>5 {exit;}',
                'address-sample.csv'
            ];

            await Module({ arguments: args, locateFile, preRun, postRun });
        </script>
    </head>
    <body>
    </body>
</html>

C:\wasm\project\16-awk\awk\*.{c,h}
Linux で作成したソースコードを配置

C:\wasm\project\16-awk\awk>dir /B *.c *.h
awkgram.tab.c
b.c
lex.c
lib.c
main.c
parse.c
proctab.c
run.c
tran.c
awk.h
awkgram.tab.h
proto.h

C:\wasm\project\16-awk\address-sample.csv
ファイル を取得して配置。

実行結果

デバッガを実行しブラウザを起動すると、コンソールには以下のような出力が行われる。

Linux で実行した結果と一致していることが確認できる。

locateFile(path=16_awk.data, prefix=)
locateFile(path=16_awk.wasm, prefix=http://localhost:8080/build/Debug/)
# AWK-START
11211  Brooklyn
02903  Providence
03561  Littleton
04401  Bangor
04901  Waterville
# DONE.
0
0
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
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?