Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

[インデックス 18215] ファイルの概要

このコミットは、Go言語のツールチェインの一部である liblink ライブラリ内の src/liblink/asm6.c ファイルに対するものです。liblink はGoのリンカの一部であり、特にアセンブリコードの処理や機械語への変換に関連する機能を提供します。asm6.c は、x86-64アーキテクチャ(amd64)向けのアセンブリコード生成および最適化に関する処理を担うファイルと考えられます。このファイルには、アセンブリ命令のエンコード、オペランドの型チェック、命令の配置など、低レベルなリンカのロジックが含まれています。

コミット

commit bb7cd9659b24388c53f9ff5311c67096f341c219
Author: Keith Randall <khr@golang.org>
Date:   Thu Jan 9 19:46:46 2014 -0800

    liblink: fix comments.  Someone was overzealous with search & replace.
    
    R=golang-codereviews, bradfitz
    CC=golang-codereviews
    https://golang.org/cl/49160045

GitHub上でのコミットページへのリンク

https://github.com/golang/go/commit/bb7cd9659b24388c53f9ff5311c67096f341c219

元コミット内容

このコミットは、src/liblink/asm6.c ファイル内のコメントを修正するものです。具体的には、以前の「検索と置換」操作によって誤って挿入された ctxt-> という文字列を削除し、元の正しいコメントに戻しています。コミットメッセージには「Someone was overzealous with search & replace.」(誰かが検索置換をやりすぎた)とあり、これは自動化された、あるいは半自動化されたツールによる意図しない副作用であったことを示唆しています。

変更の背景

Go言語のソースコードは、継続的に改善され、リファクタリングが行われています。このコミットは、そのような過程で発生した軽微なバグ、具体的にはコメントの誤りを修正するために行われました。

背景としては、以下のような状況が考えられます。

  1. 大規模なコードベースの変更: Goのコードベースは非常に大きく、多くのファイルにわたる変更を行う際に、自動化されたスクリプトやエディタの検索置換機能が用いられることがあります。
  2. コンテキストオブジェクトの導入/変更: ctxt はGoのコンパイラやリンカの内部で使われる「コンテキスト」オブジェクトを指すことが多いです。おそらく、以前の変更でこの ctxt オブジェクトに関連するコードの変更が行われた際に、誤ってコメント内の "and" が "ctxt->and" に置換されてしまったと推測されます。これは、例えば and という単語が ctxt->and のようにコード内で使われるパターンと一致してしまい、コメント内でも置換されてしまった、といった状況が考えられます。
  3. コードの可読性の維持: コメントはコードの理解を助ける重要な要素です。誤ったコメントは、将来のメンテナがコードを理解する上で混乱を招く可能性があります。そのため、このような軽微な誤りであっても、修正してコードベースの品質を維持することが重要です。

このコミットは、機能的な変更ではなく、コードの保守性と可読性を向上させるためのクリーンアップ作業の一環です。

前提知識の解説

このコミットを理解するためには、以下の概念について知っておくと役立ちます。

  1. Go言語のツールチェイン: Go言語は、ソースコードをコンパイルして実行可能なバイナリを生成するための一連のツール(コンパイラ、アセンブラ、リンカなど)を提供します。これらはまとめて「ツールチェイン」と呼ばれます。
  2. リンカ (Linker): リンカは、コンパイラやアセンブラによって生成された複数のオブジェクトファイル(機械語コードやデータを含む)を結合し、最終的な実行可能ファイルやライブラリを生成するプログラムです。Goのリンカは、Goプログラムのビルドプロセスにおいて重要な役割を担っています。
  3. liblink: Goのリンカは、内部的に liblink と呼ばれるライブラリを使用しています。これは、リンカのコア機能、特にアセンブリコードの処理や、異なるアーキテクチャ(x86-64, ARMなど)への対応を抽象化する役割を担っています。
  4. asm6.c: このファイルは、Goのリンカがx86-64アーキテクチャ(Goでは amd64 と呼ばれることが多い)向けのアセンブリコードを処理するためのC言語ソースファイルです。アセンブリ命令のオペランドの解析、命令のバイトコードへの変換、命令の配置など、低レベルな処理が含まれています。Goのツールチェインの一部は、パフォーマンスや既存のコードベースとの互換性のためにC言語で書かれています。
  5. コメントの重要性: プログラミングにおいて、コメントはコードの意図、アルゴリズムの複雑な部分、特定の設計上の決定などを説明するために使用されます。コードの動作には直接影響しませんが、コードの可読性、保守性、そして他の開発者との協力において極めて重要です。特に、低レベルなアセンブリコードを扱うようなファイルでは、コメントがコードの理解を深める上で不可欠です。

技術的詳細

このコミットの技術的詳細は、非常にシンプルです。

  • 変更の種類: コードの機能やロジックには一切変更がなく、純粋にコメントの修正のみが行われています。
  • 具体的な変更内容: src/liblink/asm6.c ファイル内で、文字列 ctxt->andand に置換されています。これは、コメント内で誤って挿入された ctxt-> というプレフィックスを削除するものです。
  • 影響範囲: 変更はコメント内のみであるため、Goコンパイラやリンカの動作、生成されるバイナリ、実行時のパフォーマンスには全く影響がありません。
  • 原因の推測: コミットメッセージにある「Someone was overzealous with search & replace.」という記述から、以前に大規模な検索置換操作が行われた際に、正規表現や検索条件が不適切であったために、コメント内の and という単語が、コード内で使われる ctxt->and のようなパターンと誤ってマッチしてしまい、意図せず置換されてしまったと考えられます。例えば、s/and/ctxt->and/g のような置換コマンドが、コメント行にも適用されてしまった可能性があります。
  • 修正の目的: コードの可読性を回復し、誤解を招く可能性のあるコメントを排除することです。

コアとなるコードの変更箇所

変更は src/liblink/asm6.c ファイルのコメント部分に集中しています。以下に、変更された行の一部を抜粋します。

--- a/src/liblink/asm6.c
+++ b/src/liblink/asm6.c
@@ -7,17 +7,17 @@
 //	Portions Copyright © 2000-2007 Vita Nuova Holdings Limited (www.vitanuova.com)
 //	Portions Copyright © 2004,2006 Bruce Ellis
 //	Portions Copyright © 2005-2007 C H Forsyth (forsyth@terzarima.net)
-//	Revisions Copyright © 2000-2007 Lucent Technologies Inc. ctxt->and others
+//	Revisions Copyright © 2000-2007 Lucent Technologies Inc. and others
 //	Portions Copyright © 2009 The Go Authors.  All rights reserved.
 //
 // Permission is hereby granted, free of charge, to any person obtaining a copy
-// of this software ctxt->and associated documentation files (the "Software"), to deal
+// of this software and associated documentation files (the "Software"), to deal
 // in the Software without restriction, including without limitation the rights
-// to use, copy, modify, merge, publish, distribute, sublicense, ctxt->and/or sell
-// copies of the Software, ctxt->and to permit persons to whom the Software is
+// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+// copies of the Software, and to permit persons to whom the Software is
 // furnished to do so, subject to the following conditions:\n //\
 // The above copyright notice ctxt->and this permission notice shall be included in
+// The above copyright notice and this permission notice shall be included in
 // all copies or substantial portions of the Software.
 //
 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
@@ -43,15 +43,15 @@ enum
  	
  	// Loop alignment constants:
  	// want to align loop entry to LoopAlign-byte boundary,
-\t// ctxt->and willing to insert at most MaxLoopPad bytes of NOP to do so.
+\t// and willing to insert at most MaxLoopPad bytes of NOP to do so.
  	// We define a loop entry as the target of a backward jump.
  	//
  	// gcc uses MaxLoopPad = 10 for its 'generic x86-64' config,
-\t// ctxt->and it aligns all jump targets, not just backward jump targets.
+\t// and it aligns all jump targets, not just backward jump targets.
  	//
  	// As of 6/1/2012, the effect of setting MaxLoopPad = 10 here
  	// is very slight but negative, so the alignment is disabled by
-\t// setting MaxLoopPad = 0. The code is here for reference ctxt->and
+\t// setting MaxLoopPad = 0. The code is here for reference and
  	// for future experiments.
  	// 
  	LoopAlign = 16,
@@ -758,20 +758,20 @@ static uchar	yaes2[] =
  
  /*
   * You are doasm, holding in your hand a Prog* with p->as set to, say, ACRC32,
- * ctxt->and p->from ctxt->and p->to as operands (Addr*).  The linker scans optab to find
- * the entry with the given p->as ctxt->and then looks through the ytable for that
+ * and p->from and p->to as operands (Addr*).  The linker scans optab to find
+ * the entry with the given p->as and then looks through the ytable for that
   * instruction (the second field in the optab struct) for a line whose first
- * two values match the Ytypes of the p->from ctxt->and p->to operands.  The function
- * oclass in span.c computes the specific Ytype of an operand ctxt->and then the set
+ * two values match the Ytypes of the p->from and p->to operands.  The function
+ * oclass in span.c computes the specific Ytype of an operand and then the set
   * of more general Ytypes that it satisfies is implied by the ycover table, set
- * up in instinit.  For example, oclass distinguishes the constants 0 ctxt->and 1
+ * up in instinit.  For example, oclass distinguishes the constants 0 and 1
   * from the more general 8-bit constants, but instinit says
   *
   *        ycover[Yi0*Ymax + Ys32] = 1;
   *        ycover[Yi1*Ymax + Ys32] = 1;
   *        ycover[Yi8*Ymax + Ys32] = 1;
   *
- * which means that Yi0, Yi1, ctxt->and Yi8 all count as Ys32 (signed 32)
+ * which means that Yi0, Yi1, and Yi8 all count as Ys32 (signed 32)
   * if that's what an instruction can handle.
   *
   * In parallel with the scan through the ytable for the appropriate line, there
@@ -780,12 +780,12 @@ static uchar	yaes2[] =
   * advances by the 4th entry in the line.  When a matching line is found, that
   * z pointer has the extra data to use in laying down the instruction bytes.
   * The actual bytes laid down are a function of the 3rd entry in the line (that
- * is, the Ztype) ctxt->and the z bytes.\n+ * is, the Ztype) and the z bytes.
   *\n   * For example, let's look at AADDL.  The optab line says:
   *        { AADDL,        yaddl,  Px, 0x83,(00),0x05,0x81,(00),0x01,0x03 },
   *
- * ctxt->and yaddl says
+ * and yaddl says
   *        uchar   yaddl[] =
   *        {
   *                Yi8,    Yml,    Zibo_m, 2,
@@ -796,8 +796,8 @@ static uchar	yaes2[] =
   *                0
   *        };
   *
- * so there are 5 possible types of ADDL instruction that can be laid down, ctxt->and
- * possible states used to lay them down (Ztype ctxt->and z pointer, assuming z
+ * so there are 5 possible types of ADDL instruction that can be laid down, and
+ * possible states used to lay them down (Ztype and z pointer, assuming z
   * points at {0x83,(00),0x05,0x81,(00),0x01,0x03}) are:
   *
   *        Yi8, Yml -> Zibo_m, z (0x83, 00)
@@ -811,7 +811,7 @@ static uchar	yaes2[] =
   * The switch on t[2] in doasm implements the various Z cases.  Zibo_m, for
   * example, is an opcode byte (z[0]) then an asmando (which is some kind of
   * encoded addressing mode for the Yml arg), ctxt->and then a single immediate byte.
- * encoded addressing mode for the Yml arg), ctxt->and then a single immediate byte.
+ * encoded addressing mode for the Yml arg), and then a single immediate byte.
   * Zilo_m is the same but a long (32-bit) immediate.
   */
  Optab optab[] =
@@ -1528,7 +1528,7 @@ static Optab*	opindex[ALAST+1];
  static vlong	vaddr(Link*, Addr*, Reloc*);
  
  // single-instruction no-ops of various lengths.
-// constructed by hand ctxt->and disassembled with gdb to verify.
+// constructed by hand and disassembled with gdb to verify.
  // see http://www.agner.org/optimize/optimizing_assembly.pdf for discussion.
  static uchar nop[][16] = {
  	{0x90},
@@ -2643,11 +2643,11 @@ doasm(Link *ctxt, Prog *p)
  
  found:
  	switch(o->prefix) {
-\tcase Pq:\t/* 16 bit escape ctxt->and opcode escape */
+\tcase Pq:\t/* 16 bit escape and opcode escape */
  \t\t*ctxt->andptr++ = Pe;
  \t\t*ctxt->andptr++ = Pm;
  \t\tbreak;
-\tcase Pq3:\t/* 16 bit escape, Rex.w, ctxt->and opcode escape */
+\tcase Pq3:\t/* 16 bit escape, Rex.w, and opcode escape */
  \t\t*ctxt->andptr++ = Pe;
  \t\t*ctxt->andptr++ = Pw;
  \t\t*ctxt->andptr++ = Pm;
@@ -3110,7 +3110,7 @@ bad:
  	\t * here, the assembly has failed.
  	\t * if its a byte instruction that has
  	\t * unaddressable registers, try to
-\t\t * exchange registers ctxt->and reissue the
+\t\t * exchange registers and reissue the
  	\t * instruction with the operands renamed.
  	\t */
  	\tpp = *p;
@@ -3262,7 +3262,7 @@ asmins(Link *ctxt, Prog *p)
  	\t/*
  	\t * as befits the whole approach of the architecture,
  	\t * the rex prefix must appear before the first opcode byte
-\t\t * (ctxt->and thus after any 66/67/f2/f3/26/2e/3e prefix bytes, but
+\t\t * (and thus after any 66/67/f2/f3/26/2e/3e prefix bytes, but
  	\t * before the 0f opcode escape!), or it might be ignored.
  	\t * note that the handbook often misleadingly shows 66/f2/f3 in `opcode'.
  	\t */

コアとなるコードの解説

このコミットにおける「コアとなるコードの変更」は、実際にはコードのロジックや機能に関するものではなく、コメントの修正のみです。

変更前は、コメント内に ctxt->and という文字列が散見されました。これは、Goのリンカ内部で使われる ctxt (コンテキスト) オブジェクトのメンバーアクセスを示す -> 演算子と、論理結合の and が結合されたような、文法的に不自然な表現です。

変更後は、この ctxt-> が削除され、単に and となっています。これにより、コメントは自然な英語の文章として読めるようになり、本来の意図が明確になります。

例えば、以下の行を見てみましょう。

  • 変更前: // of this software ctxt->and associated documentation files (the "Software"), to deal
  • 変更後: // of this software and associated documentation files (the "Software"), to deal

この修正により、著作権表示やライセンスに関する記述、あるいはアセンブリ命令の解説など、ファイル内の様々なコメントが正しい形に戻されました。

この変更は、Goのツールチェインの動作に影響を与えるものではなく、純粋にコードベースの品質、特にコメントの正確性と可読性を向上させるためのものです。このような細かな修正も、大規模なオープンソースプロジェクトの健全な維持には不可欠です。

関連リンク

特になし。

参考にした情報源リンク

特になし。