// File: /workspace/github_cpp_makefile_star2_O2/btbujiangjun[P]abcdl/example/cnn.cpp
// Function: main
int main(int argc, char** argv){
    abcdl::utils::log::set_min_log_level(abcdl::utils::log::INFO);
    abcdl::utils::log::initialize_log(argc, argv);

    const std::string path = "./data/cnn.model";

    std::vector<abcdl::cnn::Layer*> layers;
    layers.push_back(new abcdl::cnn::InputLayer(28, 28));
    layers.push_back(new abcdl::cnn::ConvolutionLayer(3, 1, 5, new abcdl::framework::SigmoidActivateFunc()));
    layers.push_back(new abcdl::cnn::SubSamplingLayer(2, new abcdl::framework::MeanPooling()));
    layers.push_back(new abcdl::cnn::ConvolutionLayer(3, 1, 5, new abcdl::framework::SigmoidActivateFunc()));
//    layers.push_back(new abcdl::cnn::SubSamplingLayer(2, new abcdl::cnn::MeanPooling()));
    layers.push_back(new abcdl::cnn::OutputLayer(10, new abcdl::framework::SigmoidActivateFunc(), new abcdl::framework::CrossEntropyCost()));

    abcdl::cnn::CNN cnn;
    cnn.set_layers(layers);
	cnn.set_batch_size(1);
	cnn.set_alpha(0.1);

    //abcdl::utils::FashionMnistReader<real> helper("data");
    abcdl::utils::MnistReader<real> helper("data");
    const size_t train_size = 60000;
    const size_t test_size  = 10000;

    abcdl::algebra::MatSet train_data;
    helper.read_train_images(train_data, train_size, 30);

    abcdl::algebra::MatSet train_label;
    helper.read_train_vec_labels(train_label, train_size);

    abcdl::algebra::MatSet test_data;
    helper.read_test_images(test_data, test_size);

    abcdl::algebra::MatSet test_label;
    helper.read_test_vec_labels(test_label, test_size);

    cnn.train(train_data, train_label, test_data, test_label);
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r12
pushq %rbx
subq $0x150, %rsp            # imm = 0x150
movq %rsi, %rbx
movl %edi, %ebp
xorl %edi, %edi
callq 0x2d562
movl %ebp, %edi
movq %rbx, %rsi
callq 0x2d26c
leaq 0x266d0(%rip), %rsi     # 0x2f0b8
leaq 0x130(%rsp), %rdi
leaq 0xe0(%rsp), %rdx
callq 0x8100
xorps %xmm0, %xmm0
movaps %xmm0, (%rsp)
andq $0x0, 0x10(%rsp)
movl $0xd0, %edi
callq 0x8310
movq %rax, %r14
pushq $0x1c
popq %rdx
movq %rax, %rdi
movq %rdx, %rsi
callq 0xeb7c
leaq 0xe0(%rsp), %rsi
movq %r14, (%rsi)
movq %rsp, %rdi
callq 0x120ec
movl $0xe8, %edi
callq 0x8310
movq %rax, %r14
pushq $0x18
popq %rdi
callq 0x8310
movq %rax, %r15
xorps %xmm0, %xmm0
movaps %xmm0, (%rax)
andq $0x0, 0x10(%rax)
leaq 0x4353e(%rip), %rbx     # 0x4bfa0
movq %rbx, (%rax)
movq %rax, %rdi
addq $0x8, %rdi
callq 0xa632
leaq 0x434d0(%rip), %r12     # 0x4bf48
movq %r12, (%r15)
pushq $0x3
popq %rsi
pushq $0x1
popq %rdx
pushq $0x5
popq %rcx
movq %r14, %rdi
movq %r15, %r8
callq 0xeb9a
leaq 0xe0(%rsp), %rsi
movq %r14, (%rsi)
movq %rsp, %rdi
callq 0x120ec
movl $0xe0, %edi
callq 0x8310
movq %rax, %r14
pushq $0x8
popq %rdi
callq 0x8310
leaq 0x441da(%rip), %rcx     # 0x4cc98
addq $0x10, %rcx
movq %rcx, (%rax)
pushq $0x2
popq %rsi
movq %r14, %rdi
movq %rax, %rdx
callq 0xebf4
leaq 0xe0(%rsp), %rsi
movq %r14, (%rsi)
movq %rsp, %rdi
callq 0x120ec
movl $0xe8, %edi
callq 0x8310
movq %rax, %r14
pushq $0x18
popq %rdi
callq 0x8310
movq %rax, %r15
xorps %xmm0, %xmm0
andq $0x0, 0x10(%rax)
movaps %xmm0, (%rax)
movq %rbx, (%rax)
movq %rax, %rdi
addq $0x8, %rdi
callq 0xa632
movq %r12, (%r15)
pushq $0x3
popq %rsi
pushq $0x1
popq %rdx
pushq $0x5
popq %rcx
movq %r14, %rdi
movq %r15, %r8
callq 0xeb9a
leaq 0xe0(%rsp), %rsi
movq %r14, (%rsi)
movq %rsp, %rdi
callq 0x120ec
movl $0x138, %edi            # imm = 0x138
callq 0x8310
movq %rax, %r14
pushq $0x18
popq %rdi
callq 0x8310
movq %rax, %r15
xorps %xmm0, %xmm0
andq $0x0, 0x10(%rax)
movaps %xmm0, (%rax)
movq %rbx, (%rax)
movq %rax, %rdi
addq $0x8, %rdi
callq 0xa632
movq %r12, (%r15)
pushq $0x18
popq %rdi
callq 0x8310
movq %rax, %r12
xorps %xmm0, %xmm0
movaps %xmm0, (%rax)
andq $0x0, 0x10(%rax)
leaq 0x4348c(%rip), %rax     # 0x4c020
movq %rax, (%r12)
movq %r12, %rdi
addq $0x8, %rdi
callq 0xa632
leaq 0x43425(%rip), %rax     # 0x4bfd0
movq %rax, (%r12)
pushq $0xa
popq %rsi
movq %r14, %rdi
movq %r15, %rdx
movq %r12, %rcx
callq 0xec36
leaq 0xe0(%rsp), %rsi
movq %r14, (%rsi)
movq %rsp, %rdi
callq 0x120ec
movq $0x32, 0x40(%rsp)
movq $0x1, 0x48(%rsp)
movl $0x3dcccccd, 0x50(%rsp) # imm = 0x3DCCCCCD
xorps %xmm0, %xmm0
movups %xmm0, 0x58(%rsp)
andq $0x0, 0x68(%rsp)
leaq 0xc8(%rsp), %rdi
movq %rsp, %rsi
callq 0xecbc
leaq 0x40(%rsp), %rdi
leaq 0xc8(%rsp), %rsi
callq 0x141a8
leaq 0xc8(%rsp), %rdi
callq 0x120de
movq $0x1, 0x48(%rsp)
movl $0x3dcccccd, 0x50(%rsp) # imm = 0x3DCCCCCD
leaq 0x26487(%rip), %rsi     # 0x2f0c9
leaq 0x20(%rsp), %rdi
leaq 0x70(%rsp), %rdx
callq 0x8100
leaq 0xe0(%rsp), %rdi
leaq 0x20(%rsp), %rsi
callq 0xed0a
leaq 0x20(%rsp), %rbx
movq %rbx, %rdi
callq 0x8120
xorps %xmm0, %xmm0
movaps %xmm0, (%rbx)
andq $0x0, 0x10(%rbx)
leaq 0xe0(%rsp), %rdi
leaq 0x20(%rsp), %rsi
pushq $0x1e
popq %rcx
movl $0xea60, %edx           # imm = 0xEA60
callq 0xed86
leaq 0x70(%rsp), %rsi
xorps %xmm0, %xmm0
movaps %xmm0, (%rsi)
andq $0x0, 0x10(%rsi)
leaq 0xe0(%rsp), %rdi
pushq $0xa
popq %rcx
movl $0xea60, %edx           # imm = 0xEA60
callq 0xee50
xorps %xmm0, %xmm0
leaq 0xb0(%rsp), %rsi
movaps %xmm0, (%rsi)
andq $0x0, 0x10(%rsi)
leaq 0xe0(%rsp), %rdi
movl $0x2710, %edx           # imm = 0x2710
xorl %ecx, %ecx
callq 0xef1e
leaq 0x90(%rsp), %rsi
xorps %xmm0, %xmm0
movaps %xmm0, (%rsi)
andq $0x0, 0x10(%rsi)
leaq 0xe0(%rsp), %rdi
pushq $0xa
popq %rcx
movl $0x2710, %edx           # imm = 0x2710
callq 0xefe8
leaq 0x40(%rsp), %rdi
leaq 0x20(%rsp), %rsi
leaq 0x70(%rsp), %rdx
leaq 0xb0(%rsp), %rcx
leaq 0x90(%rsp), %r8
callq 0x1429c
leaq 0x90(%rsp), %rdi
callq 0xf766
leaq 0xb0(%rsp), %rdi
callq 0xf766
leaq 0x70(%rsp), %rdi
callq 0xf766
leaq 0x20(%rsp), %rdi
callq 0xf766
leaq 0xe0(%rsp), %rdi
callq 0xf0b6
leaq 0x40(%rsp), %rdi
callq 0xf0da
movq %rsp, %rdi
callq 0x120de
leaq 0x130(%rsp), %rdi
callq 0x8120
xorl %eax, %eax
addq $0x150, %rsp            # imm = 0x150
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
retq
movq %rax, %rbx
jmp 0x8dfb
movq %rax, %rbx
jmp 0x8e08
movq %rax, %rbx
jmp 0x8e12
movq %rax, %rbx
leaq 0x20(%rsp), %rdi
callq 0x8120
jmp 0x8e29
jmp 0x8dcb
movq %rax, %rbx
leaq 0xc8(%rsp), %rdi
callq 0x120de
jmp 0x8e29
movq %rax, %rbx
jmp 0x8e29
movq %rax, %rbx
movq %r12, %rdi
jmp 0x8de2
jmp 0x8ddc
jmp 0x8ddc
movq %rax, %rbx
movq %r15, %rdi
callq 0x82f0
jmp 0x8e4b
jmp 0x8e48
movq %rax, %rbx
leaq 0x90(%rsp), %rdi
callq 0xf766
leaq 0xb0(%rsp), %rdi
callq 0xf766
leaq 0x70(%rsp), %rdi
callq 0xf766
leaq 0x20(%rsp), %rdi
callq 0xf766
leaq 0xe0(%rsp), %rdi
callq 0xf0b6
leaq 0x40(%rsp), %rdi
callq 0xf0da
jmp 0x8e53
jmp 0x8e43
jmp 0x8e43
jmp 0x8e48
jmp 0x8e43
jmp 0x8e48
jmp 0x8e43
jmp 0x8e48
movq %rax, %rbx
jmp 0x8e53
movq %rax, %rbx
movq %r14, %rdi
callq 0x82f0
movq %rsp, %rdi
callq 0x120de
leaq 0x130(%rsp), %rdi
callq 0x8120
movq %rbx, %rdi
callq 0x84f0