OpenJDKをビルド

OpenJDK 14をビルドしてみた。

日本語版のWindowsでビルドする場合、buildjdk-spec.gmkを編集して、clコマンドの記載がある全ての箇所に/source-charset:utf-8を入れてソースコードをSJISではなく、utf-8で解釈させないといけないらしい。

上記の対応はNGで、ちゃんとconfigureする際に以下のオプションを付けなければいけないらしい。

–with-extra-cflags=/source-charset:utf-8 –with-extra-cxxflags=/source-charset:utf-8

上記に追加でソースコード上sjisにない文字を利用しているため、警告が表示されるので、–disable-warnings-as-errorsも追加して、警告をエラーとして出力させない必要がある。

最終的に打ったコマンドは以下の通り

./configure --with-extra-cflags=/source-charset:utf-8 --with-extra-cxxflags=/source-charset:utf-8 --disable-warnings- as-errors

JDK14をビルドする場合、VisualStudio2017とCygwinが要求された。

JDK10をビルドする場合は、VisualStudio2015??とCygwinなのかな…

※太字の部分は未検証…

不思議なコード

    /**
     * Returns {@code true} if the specified number is a
     * Not-a-Number (NaN) value, {@code false} otherwise.
     *
     * @param   v   the value to be tested.
     * @return  {@code true} if the value of the argument is NaN;
     *          {@code false} otherwise.
     */
    public static boolean isNaN(double v) {
        return (v != v);
    }

OpenJDK8からとってきたこのコード…。

とても不思議に感じてしまう。

vの値が NaN の場合、NaN == NaNがfalse、NaN != NaNがtrueになるらしい…

パフォーマンスのメモ

特定のシナリオで、実行速度の比較を行ってみた。

package unit;

import java.util.ArrayList;

public class PerformanceTest {

    private static final int MAX = 100000000;


    public static void main(String[] args) {
        long startTime,endTime;

        for(int i = 0; i < 5; i ++) {
            startTime = System.currentTimeMillis();
            test01();
            endTime = System.currentTimeMillis();
            System.out.println(String.format("01 %d %d %d", startTime, endTime, endTime - startTime));

            startTime = System.currentTimeMillis();
            test02();
            endTime = System.currentTimeMillis();
            System.out.println(String.format("02 %d %d %d", startTime, endTime, endTime - startTime));
        }
    }

    private static void test01() {
        ArrayList<String> list = new ArrayList<>();
        for (int i = 0; i < MAX; i++) {
            list.add("Sample");
        }
        String.join(",", list);
    }

    private static void test02() {
        String[] array = new String[MAX];
        for (int i = 0; i < MAX; i++) {
            array[i] = "Sample";
        }
        String.join(",", array);
    }
}

実行結果

01 1571513603429 1571513609400 5971
02 1571513609422 1571513615305 5883
01 1571513615305 1571513620960 5655
02 1571513620960 1571513625083 4123
01 1571513625083 1571513630927 5844
02 1571513630927 1571513634924 3997
01 1571513634924 1571513640615 5691
02 1571513640616 1571513643817 3201
01 1571513643817 1571513649441 5624
02 1571513649441 1571513654119 4678

サイズが予め決まっている場合、配列の方がListより早いかもしれない。

でも、その速さの違いは、結構小さい。

C#,gradleからビルドするサンプルを追加

gradleは、javaのコンパイルを行うためのビルドユーティリティだけど、JavaのプログラムとC#のプログラムを一体として動作させる場合、両方同じビルドツールでビルドしたいよね。

単に実現できるか調べた時のサンプルです。

C#, Roslynのサンプルを追加

[github] https://github.com/chronos2015/samples/tree/master/cs/codes/07.Roslyn

Roslynでhello,worldくらいのソースコードを生成するサンプルを作成

ex)

namespaceを定義する場合

var nameapace = SyntaxFactory.NamespaceDeclaration(SyntaxFactory.ParseName(" sample"));

クラスを定義する場合

var classDesc = SyntaxFactory.ClassDeclaration("Program").AddModifiers(SyntaxFactory.Token(SyntaxKind.PublicKeyword))

総称型を定義する場合

var classDesc = SyntaxFactory.ClassDeclaration("Program").AddTypeParameterListParameters(SyntaxFactory.TypeParameter("T")).AddModifiers(SyntaxFactory.Token(SyntaxKind.PublicKeyword))

メソッドを定義する場合

var methodDesc = SyntaxFactory.MethodDeclaration(SyntaxFactory.ParseTypeName("void"), "Main").AddModifiers(SyntaxFactory.Token(SyntaxKind.StaticKeyword))
.AddParameterListParameters(SyntaxFactory.Parameter(SyntaxFactory.Identifier("args")).WithType(SyntaxFactory.ParseTypeName(typeof(string[]).FullName)))

こんな感じで少し面倒って感じる…

Java, Terminalソフト

[github] https://github.com/chronos2015/samples/tree/master/java/codes/09.jediterm

IntellijIDEAで、jeditermというライブラリによってターミナルソフトの機能が実現されていることをヘルプを見たときに気づいてちょっと簡単に使えるのかなと思って書いてみた。

印象としてはさほど、難しくなく使えるのかなというところ。

リポジトリから取得したjarファイルの中にmainメソッドが入っているのは驚いた。

Java, SnakeYamlのサンプルを追加

[github] https://github.com/chronos2015/samples/tree/master/java/codes/07.yaml

SnakeYamlのサンプルを追加

jsonの時みたいに属性(アトリビュートを追加させてマッピングさせるのかなと思ったけど、違うみたい。)

セッターを適宜用意しとけば勝手にセットされるので、それでもいいかなぁという感じ

ところで、yamlの属性に対応するセッターが存在しない場合、例外で落ちるのはいただけないかなというのはあるけれど…。

Cmake, wxWidgetsのサンプルを追加

[github] https://github.com/chronos2015/samples/tree/master/cpp/codes/02.wxWidgets

[github] https://github.com/chronos2015/samples/tree/master/cmake/cpp/04.wxWidgets

多少課題が残っている。

◆32bit/64bitでリンクするライブラリを切り替える

◆debug/releaseによってリンクするライブラリを切り替える

◆ 不要なライブラリのリンクを廃止する

sakura editorをcmakeからvisual studio 2019でビルドしてみた.

CMakeLists.txt

cmake_minimum_required(VERSION 3.14)

project(
	sakuraEditor
)

set(CompilerFlags
        CMAKE_CXX_FLAGS
        CMAKE_CXX_FLAGS_DEBUG
        CMAKE_CXX_FLAGS_RELEASE
        CMAKE_C_FLAGS
        CMAKE_C_FLAGS_DEBUG
        CMAKE_C_FLAGS_RELEASE
        )
foreach(CompilerFlag ${CompilerFlags})
  string(REPLACE "/MD" "/MT" ${CompilerFlag} "${${CompilerFlag}}")
endforeach()

set(CMAKE_CXX_FLAGS "-DNOMINMAX")

add_executable(
	MakefileMake
	MakefileMake/MakefileMake.cpp
)

add_executable(
	HeaderMake
	HeaderMake/HeaderMake.cpp
)

file(
	GLOB_RECURSE sakura_src 
	"${CMAKE_CURRENT_SOURCE_DIR}/sakura_core/*.cpp")

add_custom_target(
	OUTPUT sakura_core/Funccode_define.h
	PRE_BUILD
	COMMAND "${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/HeaderMake -in=..\\sakura_core\\Funccode_x.hsrc -out=..\\sakura_core\\Funccode_define.h -mode=define"
)

add_executable(
	sakura
	WIN32
	"${CMAKE_CURRENT_SOURCE_DIR}/sakura_core/sakura_rc.rc"
	${sakura_src}
)

target_link_libraries(
	sakura
	Imm32 shlwapi mpr comctl32 imagehlp)

target_include_directories(
	sakura
	PUBLIC
	"${CMAKE_CURRENT_SOURCE_DIR}/sakura_core"
)

Visual Studio 2019でビルドした際にエラーになる箇所の修正

sakura_core_main\WinMain.cpp

// 28行目の下に以下を追記
#include <locale.h>

sakura_core\util\string_ex.cpp

// 5行目の下に以下を追記
#include <locale.h>