Hatena::ブログ(Diary)

ablog このページをアンテナに追加 RSSフィード

2018-11-12

ECS で EC2 と Fargate の起動タイプのタスクを併用して同じアプリケーションを実行する

ECSEC2 と Fargate の起動タイプのタスクを併用して同じアプリケーションを実行してみた。ワークロードがない場合は、EC2 の1タスクだけ実行され(Fargate のタスクは 0)、EC2CPU使用率が50%を超えると EC2 に1タスク追加され、EC2CPU使用率が80% を超えると Fargate のタスクが追加されていくというのを試してみた。


EC2インスタンスから ab で負荷をかけて、

f:id:yohei-a:20181115013739p:image:w640

ECSEC2 インスタンスログインして htop でワークロードを確認するとこんな感じ。

f:id:yohei-a:20181115013720p:image:w640

CloudWatch のダッシュボードを見るとこんな感じで、CPU使用率が上がり、

f:id:yohei-a:20181115014144p:image:w640

ECSEC2 は +1、Fargate は +1 タスクがスケールアウトしている。

f:id:yohei-a:20181115013658p:image:w640

手順は以下の通り。


準備

キーペア作成
  • ECSを利用するリージョンでキーペアを作成していない場合は作成しておく。
セキュリティグループ作成
タイププロトコルポート範囲ソース
HTTPTCP80マイIP
SSHTCP22マイIP
すべてのTCPTCPすべて自分自身のセキュリティグループID

ELB

ELB作成

ECS

ECSタスク定義(EC2タイプ)作成
ECSタスク定義(Fargateタイプ)作成
クラスター作成
サービス(EC2起動タイプ)作成
  • 起動タイプ: EC2
  • タスク定義: ec2-task
  • クラスター: ec2-fg-mix-cluster
  • サービス名: ec2-service
  • タスクの数: 1
  • ELBタイプ: Application Load Balancer
  • ELB名: ec2-fg-mix-alb
  • パスパターン: /
  • 評価順:1
  • ヘルスチェックパス: /
  • Service Auto Scaling: Service Auto Scaling の設定を変更することで、サービスの必要数を調整する
  • タスクの最小数: 1
  • タスクの最大数: 2
  • 自動タスクスケーリングポリシー
    • ポリシー名: EC2ScaleOutPolicy
      • 既存のアラームの使用: EC2ScaleOutAlarm
      • スケーリングアクション: 追加 1 tasks、次の条件の場合 50 <= CPUUtilization
      • クールダウン期間: 30
    • ポリシー名: EC2ScaleInPolicy
      • 既存のアラームの使用: EC2ScaleInAlarm
      • スケーリングアクション: 削除 1 tasks、次の条件の場合 40 <= CPUUtilization
      • クールダウン期間: 30
サービス(FARGATE起動タイプ)作成
  • 起動タイプ: FARGATE
  • タスク定義: fargate-task
  • クラスター: ec2-fg-mix-cluster
  • サービス名: fg-service
  • タスクの数: 1
  • クラスター VPC: デフォルトVPC
  • サブネット: ap-northeast-1a のサブネット
  • パブリック IP の自動割り当て: ENABLED
  • セキュリティグループ: ECS-SG
  • ELBタイプ: Application Load Balancer
  • ELB名: ec2-fg-mix-alb
  • パスパターン: /
  • 評価順:1
  • ヘルスチェックパス: /
  • Service Auto Scaling: Service Auto Scaling の設定を変更することで、サービスの必要数を調整する
  • タスクの最小数: 1
  • タスクの最大数: 10
  • 自動タスクスケーリングポリシー
    • ポリシー名: FgScaleOutPolicy
      • 既存のアラームの使用: FgScaleOutAlarm
      • スケーリングアクション: 追加 1 tasks、次の条件の場合 80 <= CPUUtilization
      • クールダウン期間: 30
    • ポリシー名: Fg2ScaleInPolicy
      • 既存のアラームの使用: FgScaleInAlarm
      • スケーリングアクション: 削除 1 tasks、次の条件の場合 70 <= CPUUtilization
      • クールダウン期間: 30

CloudWatch Alarm

EC2起動タイプのスケールアウト用
  • 名前: EC2ScaleOutAlarm
  • CPUUtilization: >= 50
  • 期間: 1 / 1 データポイント
  • アクション
    • アラームが次の時: 警告
    • リソースタイプから: EC2 Container Service
    • 次から: service/ec2-fg-mix-cluster/ec2-service
    • 次のアクションを実行: EC2ScaleOutPolicy
EC2起動タイプのスケールイン用
  • 名前: EC2ScaleInAlarm
  • CPUUtilization: <= 40
  • 期間: 1 / 1 データポイント
  • アクション
    • アラームが次の時: 警告
    • リソースタイプから: EC2 Container Service
    • 次から: service/ec2-fg-mix-cluster/ec2-service
    • 次のアクションを実行: EC2ScaleInPolicy
Fargate起動タイプのスケールアウト用
  • 名前: FgScaleOutAlarm
  • CPUUtilization: >= 80
  • 期間: 1 / 1 データポイント
  • アクション
    • アラームが次の時: 警告
    • リソースタイプから: EC2 Container Service
    • 次から: service/ec2-fg-mix-cluster/fg-service
    • 次のアクションを実行: FgScaleOutPolicy
Fargate起動タイプのスケールイン用
  • 名前: FgScaleInAlarm
  • CPUUtilization: <= 70
  • 期間: 1 / 1 データポイント
  • アクション
    • アラームが次の時: 警告
    • リソースタイプから: EC2 Container Service
    • 次から: service/ec2-fg-mix-cluster/fg-service
    • 次のアクションを実行: FgScaleInPolicy

負荷をかけてスケールアウト/インを試す

$ sudo yum -y install htop 
$ sudo yum -y install httpd
  • 負荷をかける
$ ab -k -n 900000000 -c 100 http://*****.ap-northeast-1.elb.amazonaws.com/ &
$ ab -k -n 900000000 -c 100 http://*****.ap-northeast-1.elb.amazonaws.com/ &
$ ab -k -n 900000000 -c 100 http://*****.ap-northeast-1.elb.amazonaws.com/ &
$ ab -k -n 900000000 -c 100 http://*****.ap-northeast-1.elb.amazonaws.com/ &
$ ab -k -n 900000000 -c 100 http://*****.ap-northeast-1.elb.amazonaws.com/ &
$ ab -k -n 900000000 -c 100 http://*****.ap-northeast-1.elb.amazonaws.com/ &

補足

  • ECSのサービスを作成時にスケールアウト/インポリシーを仮で作成後に、CloudWatch Alarm でスケールアウト/インのアラームを作成し、ECSのサービスを更新して作成した CloudWatch Alarm と紐付ける。
  • 同じサービス名で削除して作り直すとマネジメントコンソールでは消えていても、バックグラウンドで削除完了していないと "Unable to Start a service that is still Draining." というエラーになる模様。しばらくして作り直すと成功した。
  • 同一クラスターEC2とFARGATEのタスク共存させる場合に以下のネットワークモードの組合せは可能なことを確認済。
  • 起動タイプがEC2ネットワークモードを awsvpc にした場合、1タスクで1つのENIを使うので、EC2インスタンスの ENI の最大数を超えるタスクを起動することはできない。ENIの最大数を超えるタスクを起動しようとすると RESOURCE:ENI エラーが発生する。

RESOURCE:* (container instance ID)

タスクによってリクエストされたリソースは、指定したコンテナインスタンスで使用できません。リソースCPU、メモリ、ポート、または Ellastic Network Interface の場合は、コンテナインスタンスクラスターへの追加が必要になる場合があります。RESOURCE:ENI エラーの場合、awsvpc ネットワークモードを使用するタスクで必要な Elastic Network Interface アタッチメントポイントが、クラスターで利用できないことを示しています。Amazon EC2 インスタンスにアタッチできるネットワークインターフェイスの数には制限があり、プライマリネットワークインターフェイスも 1 つ分としてカウントされます。各インスタンスタイプでサポートされる Network Interface の数の詳細については、Linux インスタンスAmazon EC2 ユーザーガイドの「各インスタンスタイプのネットワークインターフェイスごとの IP アドレス」を参照してください。

API failures エラーメッセージ - Amazon Elastic Container Service

2018-11-04

Parquet ファイルに Presto でクエリ時の Column Projection について調べた

確認したかったこと

  • Parquet ファイルに対して Presto で select count(year) のように特定カラムのみ参照するとそのカラムのみをストレージから読んでいる。
  • select count(*) すると Parquet ファイルのフッターのメタデータ(Row group の num rows)のみをストレージから読んでいる。

検証シナリオ

#クエリ
1select count(*) from amazon_reviews_parquet
2select count(year) from amazon_reviews_parquet
3select count(review_body) from amazon_reviews_parquet
4select * from amazon_reviews_parquet limit 10000
5select year from amazon_reviews_parquet limit 10000
6select review_body from amazon_reviews_parquet limit 10000

検証ポイント

Presto のスキャンサイズ
システムコール
$ sudo iotop
$ sudo csysdig
Linux カーネルのブロックレイヤーI/O
  • iostat で見たI/O量が select count(year) より select count(review_body) のほうが多いこと
  • blktrace + btt で見たI/O量が select count(year) より select count(review_body) のほうが多いこと
$ sudo mount -t debugfs none /sys/kernel/debug
$ sudo blktrace -w 60 -d /dev/nvme1n1p2 -o nvme1n1p2
$ sudo btt -i nvme1n1p2.blktrace.0 -B nvme1n1p2.blktrace.0.btt
ハイパーバイザーレイヤーI/O
  • EC2I/O 量が select count(year) より select count(review_body) のほうが多いこと
観測面から見える実装
$ ps -u hdfs
$ sudo ~/perf-map-agent/bin/perf-java-top <PID>
ソースコードの実装
  • Presto から HDFS に対してリクエストを出すコード
  • HDFS のランダムアクセスAPI
  • HDFSファイルシステムからランダムアクセスするコード
  • Sさんに教えてもらったやつ

環境


参考

  • Parquet ファイルの定義
$ aws s3 cp s3://amazon-reviews-pds/parquet/product_category=Apparel/part-00000-495c48e6-96d6-4650-aa65-3c36a3516ddd.c000.snappy.parquet ./
$ java -jar parquet-tools-1.6.0.jar meta ~/part-00000-495c48e6-96d6-4650-aa65-3c36a3516ddd.c000.snappy.parquet
file:              file:/Users/azekyohe/part-00000-495c48e6-96d6-4650-aa65-3c36a3516ddd.c000.snappy.parquet
creator:           parquet-mr version 1.8.2 (build c6522788629e590a53eb79874b95f6c3ff11f16c)
extra:             org.apache.spark.sql.parquet.row.metadata = {"type":"struct","fields":[{"name":"marketplace","type":"string","nullable":true,"metadata":{}},{"name":"customer_id","type":"string","nullable":true,"metadata":{}},{"name":"review_id","type":"string","nullable":true,"metadata":{}},{"name":"product_id","type":"string","nullable":true,"metadata":{}},{"name":"product_parent","type":"string","nullable":true,"metadata":{}},{"name":"product_title","type":"string","nullable":true,"metadata":{}},{"name":"star_rating","type":"integer","nullable":true,"metadata":{}},{"name":"helpful_votes","type":"integer","nullable":true,"metadata":{}},{"name":"total_votes","type":"integer","nullable":true,"metadata":{}},{"name":"vine","type":"string","nullable":true,"metadata":{}},{"name":"verified_purchase","type":"string","nullable":true,"metadata":{}},{"name":"review_headline","type":"string","nullable":true,"metadata":{}},{"name":"review_body","type":"string","nullable":true,"metadata":{}},{"name":"review_date","type":"date","nullable":true,"metadata":{}},{"name":"year","type":"integer","nullable":true,"metadata":{}}]}

file schema:       spark_schema
--------------------------------------------------------------------------------
marketplace:       OPTIONAL BINARY O:UTF8 R:0 D:1
customer_id:       OPTIONAL BINARY O:UTF8 R:0 D:1
review_id:         OPTIONAL BINARY O:UTF8 R:0 D:1
product_id:        OPTIONAL BINARY O:UTF8 R:0 D:1
product_parent:    OPTIONAL BINARY O:UTF8 R:0 D:1
product_title:     OPTIONAL BINARY O:UTF8 R:0 D:1
star_rating:       OPTIONAL INT32 R:0 D:1
helpful_votes:     OPTIONAL INT32 R:0 D:1
total_votes:       OPTIONAL INT32 R:0 D:1
vine:              OPTIONAL BINARY O:UTF8 R:0 D:1
verified_purchase: OPTIONAL BINARY O:UTF8 R:0 D:1
review_headline:   OPTIONAL BINARY O:UTF8 R:0 D:1
review_body:       OPTIONAL BINARY O:UTF8 R:0 D:1 ★
review_date:       OPTIONAL INT32 O:DATE R:0 D:1
year:              OPTIONAL INT32 R:0 D:1 ★

row group 1:       RC:589900 TS:192293412 OFFSET:4
--------------------------------------------------------------------------------
marketplace:        BINARY SNAPPY DO:0 FPO:4 SZ:231/221/0.96 VC:589900 ENC:RLE,BIT_PACKED,PLAIN_DICTIONARY
customer_id:        BINARY SNAPPY DO:0 FPO:235 SZ:4581545/6957912/1.52 VC:589900 ENC:RLE,PLAIN,BIT_PACKED
review_id:          BINARY SNAPPY DO:0 FPO:4581780 SZ:8637455/10463253/1.21 VC:589900 ENC:RLE,PLAIN,BIT_PACKED
product_id:         BINARY SNAPPY DO:0 FPO:13219235 SZ:5034158/8259079/1.64 VC:589900 ENC:RLE,PLAIN,BIT_PACKED
product_parent:     BINARY SNAPPY DO:0 FPO:18253393 SZ:5187236/7484331/1.44 VC:589900 ENC:RLE,PLAIN,BIT_PACKED,PLAIN_DICTIONARY
product_title:      BINARY SNAPPY DO:0 FPO:23440629 SZ:21585566/34792104/1.61 VC:589900 ENC:RLE,PLAIN,BIT_PACKED,PLAIN_DICTIONARY
star_rating:        INT32 SNAPPY DO:0 FPO:45026195 SZ:221797/221763/1.00 VC:589900 ENC:RLE,BIT_PACKED,PLAIN_DICTIONARY
helpful_votes:      INT32 SNAPPY DO:0 FPO:45247992 SZ:276866/558457/2.02 VC:589900 ENC:RLE,BIT_PACKED,PLAIN_DICTIONARY
total_votes:        INT32 SNAPPY DO:0 FPO:45524858 SZ:306153/590359/1.93 VC:589900 ENC:RLE,BIT_PACKED,PLAIN_DICTIONARY
vine:               BINARY SNAPPY DO:0 FPO:45831011 SZ:962/1025/1.07 VC:589900 ENC:RLE,BIT_PACKED,PLAIN_DICTIONARY
verified_purchase:  BINARY SNAPPY DO:0 FPO:45831973 SZ:62135/74471/1.20 VC:589900 ENC:RLE,BIT_PACKED,PLAIN_DICTIONARY
review_headline:    BINARY SNAPPY DO:0 FPO:45894108 SZ:8309372/14205327/1.71 VC:589900 ENC:RLE,PLAIN,BIT_PACKED,PLAIN_DICTIONARY
review_body:        BINARY SNAPPY DO:0 FPO:54203480 SZ:66263112/107760057/1.63 VC:589900 ENC:RLE,PLAIN,BIT_PACKED
review_date:        INT32 SNAPPY DO:0 FPO:120466592 SZ:70391/738861/10.50 VC:589900 ENC:RLE,BIT_PACKED,PLAIN_DICTIONARY
year:               INT32 SNAPPY DO:0 FPO:120536983 SZ:9111/186192/20.44 VC:589900 ENC:RLE,BIT_PACKED,PLAIN_DICTIONARY

準備手順

データを S3 から HDFS にコピーする
$ ssh -i ~/mykey.pem hadoop@ec2-**-***-***-233.compute-1.amazonaws.com
  • hdfs ユーザーにスイッチする。
$ sudo su - hdfs
$ hadoop fs -mkdir /amazon-reviews-pds
  • データを S3 から HDFS にコピーする。
$ nohup s3-dist-cp --src  s3://amazon-reviews-pds/ --dest /amazon-reviews-pds  &
外部テーブルを定義する。
$ hive
> create database if not exists parquet;
^H> show databases;
> use parquet;
  • テーブルを作成する。
> CREATE EXTERNAL TABLE parquet.amazon_reviews_parquet(
  marketplace string, 
  customer_id string, 
  review_id string, 
  product_id string, 
  product_parent string, 
  product_title string, 
  star_rating int, 
  helpful_votes int, 
  total_votes int, 
  vine string, 
  verified_purchase string, 
  review_headline string, 
  review_body string, 
  review_date bigint, 
  year int)
PARTITIONED BY (product_category string)
ROW FORMAT SERDE 
  'org.apache.hadoop.hive.ql.io.parquet.serde.ParquetHiveSerDe' 
STORED AS INPUTFORMAT 
  'org.apache.hadoop.hive.ql.io.parquet.MapredParquetInputFormat' 
OUTPUTFORMAT 
  'org.apache.hadoop.hive.ql.io.parquet.MapredParquetOutputFormat'
LOCATION
  'hdfs:///amazon-reviews-pds/parquet';
> MSCK REPAIR TABLE parquet.amazon_reviews_parquet;
> quit;
  • クエリを実行できることを確認する。
$ presto-cli
presto> use hive.parquet;
presto:parquet> select count(*) from amazon_reviews_parquet;
presto:parquet> select count(year) from amazon_reviews_parquet;
presto:parquet> select count(review_body) from amazon_reviews_parquet;

性能情報取得ツールインストール
$ sudo yum -y install htop sysstat dstat iotop ltrace strace perf blktrace gnuplot
$ sudo yum -y install cmake
$ git clone --depth=1 https://github.com/jrudolph/perf-map-agent
$ cd perf-map-agent
$ cmake .
$ make
  • FlameGraph
$ git clone https://github.com/brendangregg/FlameGraph
$ chmod +x FlameGraph/*.pl
$ vi ~/.bashrc
export FLAMEGRAPH_DIR=~/FlameGraph

*1VPN経由でアクセスできない

2018-10-27

EBS ボリュームの CMK を KMS で生成したものから BYOK に変更する

EBS ボリュームの CMK(Customer Master Key) を KMS で生成したものから BYOK(Bring Your Own Key) したものに変更してみた。EBS のスナップショットを取得して、スナップショットをコピーする際に CMK を変更し、EBS ボリュームを作成して EC2 にアタッチすることで CMK を変更できた。


手順

KMSにキーを作成する
  • CMK を作成する。
$ aws kms create-key
{
    "KeyMetadata": {
        "Origin": "AWS_KMS",
        "KeyId": "2ae86c99-8b8f-4bba-9998-005b2dd768ac",
        "Description": "",
        "KeyManager": "CUSTOMER",
        "Enabled": true,
        "KeyUsage": "ENCRYPT_DECRYPT",
        "KeyState": "Enabled",
        "CreationDate": 1540638331.395,
        "Arn": "arn:aws:kms:ap-northeast-1:123456789012:key/2ae86c99-8b8f-4bba-9998-005b2dd768ac",
        "AWSAccountId": "123456789012"
    }
}
  • エイリアス名をつける。
$ aws kms create-alias --alias-name alias/ebs-kms-key --target-key-id 2ae86c99-8b8f-4bba-9998-005b2dd768ac
EC2インスタンスを作成する

f:id:yohei-a:20181027201557p:image

  • EBSのボリュームを初期化してマウントする
$ sudo mkfs -t ext4 /dev/sdb
$ sudo mkdir /ebs-enc
$ sudo chmod o+w /ebs-enc
$ sudo vi /etc/fstab
/dev/sdb    /ebs-enc    ext4    defaults        1   1 # 追記
$ sudo mount -a
$ df -h
Filesystem      Size  Used Avail Use% Mounted on
devtmpfs        3.9G   68K  3.9G   1% /dev
tmpfs           3.9G     0  3.9G   0% /dev/shm
/dev/xvda1      7.8G  1.1G  6.7G  14% /
/dev/xvdb        59G   52M   56G   1% /ebs-enc
EBSボリュームにデータを置く
$ aws s3 ls --recursive --human-readable --summarize s3://amazon-reviews-pds/tsv
(中略)
Total Objects: 55
   Total Size: 32.2 GiB
$ aws s3 cp --recursive s3://amazon-reviews-pds/tsv /ebs-enc/
$ ls -lh /ebs-enc|head -5
total 33G
-rw-rw-r-- 1 ec2-user ec2-user 231M Nov 24  2017 amazon_reviews_multilingual_DE_v1_00.tsv.gz
-rw-rw-r-- 1 ec2-user ec2-user  68M Nov 24  2017 amazon_reviews_multilingual_FR_v1_00.tsv.gz
-rw-rw-r-- 1 ec2-user ec2-user  91M Nov 24  2017 amazon_reviews_multilingual_JP_v1_00.tsv.gz
-rw-rw-r-- 1 ec2-user ec2-user 334M Nov 24  2017 amazon_reviews_multilingual_UK_v1_00.tsv.gz
KMSにCMKをBYOKする
  • KMS に CMK を空で作成する。
$ aws kms create-key --origin EXTERNAL --description byok_key
{
    "KeyMetadata": {
        "Origin": "EXTERNAL",
        "KeyId": "35e6c88a-0cd9-4614-9e7a-ec5782d7c1da",
        "Description": "byok_key",
        "KeyManager": "CUSTOMER",
        "Enabled": false,
        "KeyUsage": "ENCRYPT_DECRYPT",
        "KeyState": "PendingImport",
        "CreationDate": 1540639989.29,
        "Arn": "arn:aws:kms:ap-northeast-1:123456789012:key/35e6c88a-0cd9-4614-9e7a-ec5782d7c1da",
        "AWSAccountId": "123456789012"
    }
}
  • 作成した CMK にエイリアス名をつける。
$ aws kms create-alias --alias-name alias/ebs-byok-key --target-key-id 35e6c88a-0cd9-4614-9e7a-ec5782d7c1da
  • PublicKey と ImportToken をダウンロードする。
$ aws kms get-parameters-for-import \
--key-id 35e6c88a-0cd9-4614-9e7a-ec5782d7c1da \
--wrapping-algorithm RSAES_PKCS1_V1_5 \
--wrapping-key-spec RSA_2048
  • 上記のPublicKey を PublicKey.b64、ImportToken を ImportToken.b64 というファイル名で保存する。
  • PublicKey と ImportToken をそれぞれbase64デコードして、新しいファイルで保存する。
$ openssl enc -d -a -A -in PublicKey.b64 -out PublicKey.bin
$ openssl enc -d -a -A -in ImportToken.b64 -out ImportToken.bin
  • KMS にインポートする CMK を作成する
$ openssl rand -out PlaintextKeyMaterial.bin 32
  • 生成した CMK を、デコードした PublicKey を使って暗号化する。
$ openssl rsautl -encrypt \
-in PlaintextKeyMaterial.bin \
-pkcs \
-inkey PublicKey.bin \
-keyform DER \
-pubin \
-out EncryptedKeyMaterial.bin
  • 暗号化した CMK を KMS にインポートする。
$ aws kms import-key-material --key-id 35e6c88a-0cd9-4614-9e7a-ec5782d7c1da \
--encrypted-key-material fileb://EncryptedKeyMaterial.bin \
--import-token fileb://ImportToken.bin \
--expiration-model KEY_MATERIAL_EXPIRES \
--valid-to 2018-11-01T00:00:00-00:00

f:id:yohei-a:20181027204448p:image

EBSをBYOKしたCMKで暗号化し直す
  • アンマウントする。
$ sudo umount /ebs-enc
  • スナップショットを取得する。

f:id:yohei-a:20181027205349p:image

  • スナップショット取得完了を確認する。

f:id:yohei-a:20181027213441p:image

  • スナップショットを選択して、[アクション]-[コピー]を選択して[マスターキー]をBYOKしたCMKに変更して[コピー]をクリックする。

f:id:yohei-a:20181027213853p:image

  • スナップショットのコピーが完了したら、

f:id:yohei-a:20181027214959p:image

  • BYOKで暗号化したスナップショットを選択して、[アクション]-[ボリュームの作成]を選択して、スナップショットからEBSボリュームを作成する

f:id:yohei-a:20181027215058p:image

f:id:yohei-a:20181027215451p:image

  • 作成したEBSボリュームがBYOKしたCMKで暗号化されていることを確認する。

f:id:yohei-a:20181027220822p:image

  • EBSボリュームをマウントして確認する。
$ sudo mkdir /ebs-byok
$ sudo chmod o+w /ebs-byok
$ sudo vi /etc/fstab
/dev/sdf   /ebs-byok    ext4   defaults        1   1 #追記
$ sudo mount -a
$ df -h
Filesystem      Size  Used Avail Use% Mounted on
devtmpfs        3.9G   72K  3.9G   1% /dev
tmpfs           3.9G     0  3.9G   0% /dev/shm
/dev/xvda1      7.8G  1.1G  6.7G  14% /
/dev/xvdb        59G   33G   24G  58% /ebs-enc
/dev/xvdf        59G   33G   24G  58% /ebs-byok
$ cd /ebs-byok
$ ls -lh|head -5
total 33G
-rw-rw-r-- 1 ec2-user ec2-user 231M Nov 24  2017 amazon_reviews_multilingual_DE_v1_00.tsv.gz
-rw-rw-r-- 1 ec2-user ec2-user  68M Nov 24  2017 amazon_reviews_multilingual_FR_v1_00.tsv.gz
-rw-rw-r-- 1 ec2-user ec2-user  91M Nov 24  2017 amazon_reviews_multilingual_JP_v1_00.tsv.gz
-rw-rw-r-- 1 ec2-user ec2-user 334M Nov 24  2017 amazon_reviews_multilingual_UK_v1_00.tsv.gz
  • ファーストタッチペナルティを回避するためブロックデバイスのデータにアクセスする。
$ sudo dd if=/dev/xvdf of=/dev/null bs=1M

参考

2018-10-17

perf-map-agent 実行時に "AttachNotSupportedException: Unable to open socket file" と怒られる

事象

perf-map-agent をビルドして

$ sudo yum -y install cmake
$ git clone --depth=1 https://github.com/jvm-profiling-tools/perf-map-agent
$ cd perf-map-agent
$ cmake .
$ make
$ cd out

/etc/hadoop/conf/ 以下の hadoop-env.sh, yarn-env.sh にexport HADOOP_OPTS="... -XX:+PreserveFramePointer" export YARN_OPTS="... -XX:+PreserveFramePointer" を追加して、hdfs の jvm を kill して再起動。ps で -XX:+PreserveFramePointer が入っていることを確認してから、hdfsプロセスにアタッチしようとすると "AttachNotSupportedException: Unable to open socket file" と怒られる

$ ps -elf|grep hdfs
$ sudo -u hdfs java -cp attach-main.jar:$JAVA_HOME/lib/tools.jar net.virtualvoid.perf.AttachOnce 6362
Exception in thread "main" http://com.sun.tools .attach.AttachNotSupportedException: Unable to open socket file: target process not responding or HotSpot VM not loaded

調査

スモールケースで調べてみた。

カレントディレクトリを perf-map-agent/out にして、

$ cd /home/hadoop/perf-map-agent/out

DoWhileTrueJava.java を作成して

public class DoWhileTrueJava {
	public static void main(String[] args) throws InterruptedException {
		System.out.println("Start Processing inside do while loop");
		do {
			Thread.sleep(5 * 1000);
		} while (true);
	}
}

コンパイルして

$ javac DoWhileTrueJava.java

DoWhileTrueJava を実行して

$ java  DoWhileTrueJava &
[2] 3995
Start Processing inside do while loop

perf-map-agent で DoWhileTrueJava のJavaプロセスにアタッチしてみると、NoClassDefFoundError で怒られる。

$ java -cp attach-main.jar:$JAVA_HOME/lib/tools.jar net.virtualvoid.perf.AttachOnce 3995
Error: A JNI error has occurred, please check your installation and try again
Exception in thread "main" java.lang.NoClassDefFoundError: com/sun/tools/attach/AgentInitializationException
	at java.lang.Class.getDeclaredMethods0(Native Method)
	at java.lang.Class.privateGetDeclaredMethods(Class.java:2701)
	at java.lang.Class.privateGetMethodRecursive(Class.java:3048)
	at java.lang.Class.getMethod0(Class.java:3018)
	at java.lang.Class.getMethod(Class.java:1784)
	at sun.launcher.LauncherHelper.validateMainClass(LauncherHelper.java:544)
	at sun.launcher.LauncherHelper.checkAndLoadMain(LauncherHelper.java:526)
Caused by: java.lang.ClassNotFoundException: com.sun.tools.attach.AgentInitializationException
	at java.net.URLClassLoader.findClass(URLClassLoader.java:381)
	at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
	at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:349)
	at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
	... 7 more

あら、$JAVA_HOME/lib/tools.jar がない

$ ls -l $JAVA_HOME/lib/tools.jar
ls: cannot access /etc/alternatives/jre/lib/tools.jar: No such file or directory

探すと見つかったので、

$ sudo find /usr -name tools.jar
/usr/lib/jvm/java-1.8.0-openjdk-1.8.0.181-8.b13.39.39.amzn1.x86_64/lib/tools.jar

お、成功した

$ java -cp /home/hadoop/perf-map-agent/out/attach-main.jar:/usr/lib/jvm/java-1.8.0-openjdk-1.8.0.181-8.b13.39.39.amzn1.x86_64/lib/tools.jar net.virtualvoid.perf.AttachOnce 3995

うまくいってますね

$ head /tmp/perf-3995.map
7fb5ad000060 1d flush_icache_stub
7fb5ad000160 21b get_cpu_info_stub
7fb5ad000420 3f forward exception
7fb5ad00045f e8 call_stub
7fb5ad000547 1f catch_exception
7fb5ad000566 5 atomic_xchg
7fb5ad00056b 7 atomic_xchg_ptr
7fb5ad000572 7 atomic_cmpxchg
7fb5ad000579 9 atomic_cmpxchg_long
7fb5ad000582 9 atomic_add

hdfsプロセスに対しても成功

$ ps -elf|grep hdfs
$ sudo -u hdfs java -cp /home/hadoop/perf-map-agent/out/attach-main.jar:/usr/lib/jvm/java-1.8.0-openjdk-1.8.0.181-8.b13.39.39.amzn1.x86_64/lib/tools.jar net.virtualvoid.perf.AttachOnce 8837

情報とれてますね

$ head /tmp/perf-8837.map
7f1989000060 1d flush_icache_stub
7f1989000160 21b get_cpu_info_stub
7f1989000420 3f forward exception
7f198900045f e8 call_stub
7f1989000547 1f catch_exception
7f1989000566 5 atomic_xchg
7f198900056b 7 atomic_xchg_ptr
7f1989000572 7 atomic_cmpxchg
7f1989000579 9 atomic_cmpxchg_long
7f1989000582 9 atomic_add

関連


参考

2018-10-08

EC2に Netflix Vector をインストールしてみた

EC2 に Netflix Vector をインストールしてみた。


インストール・設定

$ sudo yum -y install git flex bison libmicrohttpd libmicrohttpd-devel http-parser atlas-sse3-devel
$ git clone https://github.com/performancecopilot/pcp.git
$ cd pcp
$ ./configure --prefix=/usr --sysconfdir=/etc --localstatedir=/var --with-webapi
$ sudo make
$ sudo groupadd -r pcp
$ sudo useradd -c "Performance Co-Pilot" -g pcp -d /var/lib/pcp -M -r -s /usr/sbin/nologin pcp
$ sudo  make install
  • pcpの起動
$ sudo service pmcd start
$ sudo service pmwebd start
$ sudo yum -y install httpd
$ sudo service httpd start
$ cd /var/www/html
$ sudo wget https://dl.bintray.com/netflixoss/downloads/1.3.1/vector.tar.gz
$ sudo tar xvzf vector.tar.gz
$ sudo chown -R apache:apache dist
$ mv dist/* ./

性能情報を確認する

f:id:yohei-a:20181008231740p:image


参考


追記(2018/11/04):

上記の手順でインストールして、sudo service pmcd start で以下のエラーが発生したが、

$ sudo service pmcd start
Rebuilding PMNS ... /usr/libexec/pcp/bin/pmnsmerge: error while loading shared libraries: libpcp.so.3: cannot open shared object file: No such file or directory
Rebuilding the Performance Metrics Name Space (PMNS) in /var/lib/pcp/pmns ...
Rebuild: PCP upgrade processing for "root" PMNS changes ...
Rebuild: merging the following PMNS files:
root root_jbd2 root_kvm root_linux root_mmv root_pmcd root_proc root_root root_xfs
Rebuild: pmnsmerge failed
         "root" has not been changed.
failed (status=1)
Starting pmcd ... /usr/libexec/pcp/bin/pmcd: error while loading shared libraries: libpcp_pmda.so.3: cannot open shared object file: No such file or directory
/etc/init.d/pmcd: pmcd --verify failed, cannot start pmcd.

https://github.com/apache/incubator-mxnet/issues/5290 を参考に、atlas-sse3-devel をインストールしたら解決した。

$ sudo yum -y install atlas-sse3-devel

上記で解決しなかった場合は、find で探すと共有ライブラリは見つかったので、

[hadoop@ip-172-31-4-40 html]$ find /usr -name libpcp.so.3
/usr/lib/libpcp.so.3
[hadoop@ip-172-31-4-40 html]$ find /usr -name libpcp_pmda.so.3
/usr/lib/libpcp_pmda.so.3

共有ライブラリへのパスを通してやると解決した。

$ sudo vi /etc/ld.so.conf
/usr/lib #追記
$ sudo ldconfig
$ sudo ldconfig -v

*1セキュリティグループでアクセス許可しておく