RaziCTF 2020 Writeup

この大会は2020/10/26 14:30(JST)~2020/10/28 14:30(JST)に開催されました。
今回もチームで参戦。結果は7964点で314チーム中44位でした。
自分で解けた問題をWriteupとして書いておきます。

Sanity Check (Misc)

ルールのページにフラグが書いてある画像があった。
f:id:satou-y:20201106122633p:plain

RaziCTF{S0_iT_b3G1Ns}

720 (Misc)

添付ファイルの圧縮ファイルにはdllが6個入っている。その内、printui.dllは解凍でき、展開されたThe Flag You Need.txtにフラグが書かれていた。

RaziCTF{5pl17_4nd_j01n}

chasing a lock (Android Security)

Bytecode Viewerでデコンパイルする。

package com.example.razictf_2;

import android.view.View;
import android.view.View.OnClickListener;
import android.widget.TextView;

class MainActivity$2 implements OnClickListener {
   // $FF: synthetic field
   final MainActivity this$0;

   MainActivity$2(MainActivity var1) {
      this.this$0 = var1;
   }

   public void onClick(View var1) {
      TextView var2 = (TextView)this.this$0.findViewById(2131165190);
      int var3 = Integer.parseInt(var2.getText().toString());
      if (var3 != 0 && var3 >= 0) {
         --var3;
         String var4 = (new switcher()).run(var3);
         if (var4 != null) {
            ((TextView)this.this$0.findViewById(2131165187)).setText(var4);
         }

         var2.setText(String.valueOf(var3));
      } else {
         var2.setText("0");
      }

   }
}

package com.example.razictf_2;

public class switcher {
   public String run(int var1) {
      if (var1 == 0) {
         a1 var2 = new a1();
         StringBuilder var3 = new StringBuilder();
         var3.append(" ");
         var3.append(var2.run(var1));
         String var4 = var3.toString();
         a2 var8 = new a2();
         System.out.println(var8.run(var1));
         StringBuilder var5 = new StringBuilder();
         var5.append(var4);
         var5.append(var8.run(var1));
         String var9 = var5.toString();
         a3 var6 = new a3();
         StringBuilder var10 = new StringBuilder();
         var10.append(var9);
         var10.append(var6.run(var1));
         var9 = var10.toString();
         a4 var7 = new a4();
         var10 = new StringBuilder();
         var10.append(var9);
         var10.append(var7.run(var1));
         var4 = var10.toString();
         a5 var11 = new a5();
         var5 = new StringBuilder();
         var5.append(var4);
         var5.append(var11.run(var1));
         return var5.toString();
      } else {
         return null;
      }
   }
}

package com.example.razictf_2;

import android.util.Base64;

public class a1 {
   public String run(int var1) {
      String var2 = "Vm0wd2QyUXlVWGxWV0d4V1YwZDRWMVl3WkRSV01WbDNXa1JTVjAxV2JETlhhMUpUVmpBeFYySkVUbGhoTVVwVVZtcEJlRll5U2tWVWJHaG9UVlZ3VlZadGNFSmxSbGw1VTJ0V1ZXSkhhRzlVVmxaM1ZsWmFkR05GU214U2JHdzFWVEowVjFaWFNraGhSemxWVm14YU0xWnNXbUZqVmtaMFVteFNUbUpGY0VwV2JURXdZVEZrU0ZOclpHcFRSVXBZV1ZSR2QyRkdjRmRYYlVaclVsUkdWbFpYZUZOVWJVWTJVbFJHVjJFeVVYZFpla3BIWXpGT2RWVnRhRk5sYlhoWFZtMXdUMVF3TUhoalJscFlZbFZhY2xWcVFURlNNV1J5VjJ4T1ZXSlZjRWRaTUZaM1ZqSktWVkpZWkZkaGExcFlXa1ZhVDJNeFpITmhSMnhUVFcxb1dsWXhaRFJpTWtsNVZtNU9WbUpHV2xSWmJGWmhZMVphZEdSSFJrNVNiRm93V2xWYVQxWlhTbFpqUldSYVRVWmFNMVpxU2t0V1ZrcFpXa1p3VjFKV2NIbFdWRUpoVkRKT2MyTkZhR3BTYXpWWVZXcE9iMkl4V1hoYVJGSldUVlZzTlZaWE5VOVhSMHBJVld4c1dtSkdXbWhaTW5oWFkxWkdWVkpzVGs1V01VbzFWbXBKTVdFeFdYZE5WVlpUWVRGd1YxbHJXa3RUUmxweFVtMUdVMkpWYkRaWGExcHJZVWRGZUdOSE9WZGhhMHBvVmtSS1QyUkdTbkpoUjJoVFlYcFdlbGRYZUc5aU1XUkhWMjVTVGxOSFVuTlZha0p6VGtaVmVXUkhkRmhTTUhCSlZsZDRjMWR0U2tkWGJXaGFUVzVvV0ZsNlJsZGpiSEJIV2tkc1UySnJTbUZXTW5oWFdWWlJlRmRzYUZSaVJuQlpWbXRXZDFZeGJISlhhM1JVVW14d2VGVnRNVWRWTWtwV1lrUmFXR0V4Y0hKWlZXUkdaVWRPU0U5V1pHaGhNSEJ2Vm10U1MxUXlVa2RUYmtwaFVtMW9jRlpxU205bGJHUllaVWM1YVUxcmJEUldNV2h2V1ZaS1IxTnVRbFZXTTFKNlZHdGFZVk5IVWtoa1JtUnBWbGhDU1ZacVNqUlZNV1IwVTJ0a1dHSlhhR0ZVVnpWdlYwWnJlRmRyWkZkV2EzQjZWa2R6TVZZd01WWmlla1pYWWxoQ1RGUnJXbEpsUm1SellVWlNhVkp1UW5oV1YzaHJWVEZzVjFWc1dsaGlWVnBQVkZaYWQyVkdWWGxrUkVKWFRWWndlVmt3V25kWFIwVjRZMFJPV21FeVVrZGFWM2hIWTIxS1IxcEhiRmhTVlhCS1ZtMTBVMU14VlhoWFdHaFlZbXhhVmxsclpHOWpSbHB4VTIwNWJHSkhVbGxhVldNMVlWVXhjbUpFVWxkTmFsWlVWa2Q0YTFOR1ZuTlhiRlpYVFRGS05sWkhlR0ZXTWxKSVZXdG9hMUl5YUhCVmJHaENaREZhYzFwRVVtcE5WMUl3VlRKMGExZEhTbGhoUjBaVlZucFdkbFl3V25KbFJtUnlXa1prVjJFelFqWldhMlI2VFZaa1IxTnNXbXBTVjNoWVdXeG9RMVJHVW5KWGJFcHNVbTFTZWxsVldsTmhSVEZ6VTI1b1YxWjZSVEJhUkVaclVqSktTVlJ0YUZOaGVsWlFWa1phWVdReVZrZFdXR3hyVWtWS1dGUldXbmRsVm10M1YyNWtXRkl3VmpSWk1GSlBWMjFGZVZWclpHRldNMmhJV1RJeFMxSXhjRWhpUm1oVFZsaENTMVp0TVRCVk1VMTRWbGhvV0ZkSGFGbFpiWGhoVm14c2NscEhPV3BTYkhCNFZUSXdOV0pIU2toVmJHeGhWbGROTVZsV1ZYaGpiVXBGVld4a1RtRnNXbFZXYTJRMFlURk9SMVp1VGxoaVJscFlXV3RvUTFkV1draGxSMFpYVFd4S1NWWlhkRzloTVVwMFZXczVWMkZyV2t4Vk1uaHJWakZhZEZKdGNFNVdNVWwzVmxSS01HRXhaRWhUYkdob1VqQmFWbFp1Y0Zka2JGbDNWMjVLYkZKdFVubFhhMXByVmpKRmVsRnFXbGRoTWxJMlZGWmFXbVF3TVZkWGJXeHNZVEZ3V1ZkWGVHOVJNVkpIVlc1S1dHSkZjSE5WYlRGVFpXeHNWbGRzVG1oV2EzQXhWVmMxYjFZeFdYcGhTRXBYVmtWYWVsWnFSbGRqTVdSellVZHNWMVp1UWpaV01XUXdXVmRSZVZaclpGZFhSM2h5Vld0V1MxZEdVbGRYYm1Sc1ZteHNOVnBWYUd0WFIwcEhZMFpvV2sxSFVuWldNbmhoVjBaV2NscEhSbGRXTVVwUlZsZHdTMUl4U1hsU2EyaHBVbXMxY0ZsVVFuZE5iRnAwVFZSQ1ZrMVZNVFJXVm1oelZtMUZlVlZzV2xwaVdGSXpXVlZhVjJSSFZrWmtSM0JUWWtoQ05GWnJZM2RPVm1SSFYyNU9hbEp0ZUdGVVZWcFdUVlpzVjFaWWFHcGlWWEJHVmxkNGExUnRSbk5YYkZaWVZtMVJNRlY2Um1GamF6VlhZa1pLYVZKc2NGbFhWM1JoWkRGa1YxZHJhR3RTTUZwdlZGZHpNV1ZzV1hsT1ZrNW9UVlZzTlZsVmFFTldiVXBJWVVWT1lWSkZXbWhaZWtaM1VsWldkR05GTlZkTlZXd3pWbXhTUzAxSFJYaGFSV2hVWWtkb2IxVnFRbUZXYkZwMFpVaGtUazFXY0hsV01qRkhZV3hhY21ORVFtRlNWMUYzVm1wS1MyTnNUbkpoUm1SVFRUSm9iMVpyVWt0U01WbDRWRzVXVm1KRlNsaFZiRkpYVjFaYVIxbDZSbWxOVjFKSVdXdGFWMVZzWkVoaFJsSlZWbTFTVkZwWGVITldiR1J6Vkcxb1UxWkZXalpXVkVreFlqRlplRmRZY0ZaaVIyaFpWbTE0ZDFsV2NGWlhiWFJyVm10d2VsWnRNWE5XTVVsNllVUldWMDFYVVhkWFZtUlNaVlphY2xwR1pHbGlSWEI1VmxkMFYxTXlTWGhpUm14cVVsZFNjMVp0ZUV0bGJGcDBUVVJXV0ZJd2NFaFpNRnB2VjJzeFNHRkZlRmROYm1ob1ZqQmFWMk5zY0VoU2JHUk9UVzFvU2xZeFVrcGxSazE0VTFob2FsSlhVbWhWYlhNeFYwWlpkMVpyZEU1aVJuQXdXVEJXYTFkc1dYZFdhbEpYWWtkb2RsWXdXbXRUUjBaSFYyeHdhVmRIYUc5V2JURTBZekpPYzFwSVNtdFNNMEpVV1d0YWQwNUdXbGhOVkVKT1VteHNORll5TlU5aGJFcFlZVVpvVjJGck5WUldSVnB6VmxaR1dXRkdUbGRoTTBJMlZtdGtORmxXVlhsVGExcFlWMGhDV0Zac1duZFNNVkY0VjJ0T1ZtSkZTbFpVVlZGM1VGRTlQUT09";

      for(var1 = 0; var1 < 20; ++var1) {
         var2 = new String(Base64.decode(var2.getBytes(), 0));
      }

      return var2;
   }
}

20回base64デコードする。

enc = 'Vm0wd2QyUXlVWGxWV0d4V1YwZDRWMVl3WkRSV01WbDNXa1JTVjAxV2JETlhhMUpUVmpBeFYySkVUbGhoTVVwVVZtcEJlRll5U2tWVWJHaG9UVlZ3VlZadGNFSmxSbGw1VTJ0V1ZXSkhhRzlVVmxaM1ZsWmFkR05GU214U2JHdzFWVEowVjFaWFNraGhSemxWVm14YU0xWnNXbUZqVmtaMFVteFNUbUpGY0VwV2JURXdZVEZrU0ZOclpHcFRSVXBZV1ZSR2QyRkdjRmRYYlVaclVsUkdWbFpYZUZOVWJVWTJVbFJHVjJFeVVYZFpla3BIWXpGT2RWVnRhRk5sYlhoWFZtMXdUMVF3TUhoalJscFlZbFZhY2xWcVFURlNNV1J5VjJ4T1ZXSlZjRWRaTUZaM1ZqSktWVkpZWkZkaGExcFlXa1ZhVDJNeFpITmhSMnhUVFcxb1dsWXhaRFJpTWtsNVZtNU9WbUpHV2xSWmJGWmhZMVphZEdSSFJrNVNiRm93V2xWYVQxWlhTbFpqUldSYVRVWmFNMVpxU2t0V1ZrcFpXa1p3VjFKV2NIbFdWRUpoVkRKT2MyTkZhR3BTYXpWWVZXcE9iMkl4V1hoYVJGSldUVlZzTlZaWE5VOVhSMHBJVld4c1dtSkdXbWhaTW5oWFkxWkdWVkpzVGs1V01VbzFWbXBKTVdFeFdYZE5WVlpUWVRGd1YxbHJXa3RUUmxweFVtMUdVMkpWYkRaWGExcHJZVWRGZUdOSE9WZGhhMHBvVmtSS1QyUkdTbkpoUjJoVFlYcFdlbGRYZUc5aU1XUkhWMjVTVGxOSFVuTlZha0p6VGtaVmVXUkhkRmhTTUhCSlZsZDRjMWR0U2tkWGJXaGFUVzVvV0ZsNlJsZGpiSEJIV2tkc1UySnJTbUZXTW5oWFdWWlJlRmRzYUZSaVJuQlpWbXRXZDFZeGJISlhhM1JVVW14d2VGVnRNVWRWTWtwV1lrUmFXR0V4Y0hKWlZXUkdaVWRPU0U5V1pHaGhNSEJ2Vm10U1MxUXlVa2RUYmtwaFVtMW9jRlpxU205bGJHUllaVWM1YVUxcmJEUldNV2h2V1ZaS1IxTnVRbFZXTTFKNlZHdGFZVk5IVWtoa1JtUnBWbGhDU1ZacVNqUlZNV1IwVTJ0a1dHSlhhR0ZVVnpWdlYwWnJlRmRyWkZkV2EzQjZWa2R6TVZZd01WWmlla1pYWWxoQ1RGUnJXbEpsUm1SellVWlNhVkp1UW5oV1YzaHJWVEZzVjFWc1dsaGlWVnBQVkZaYWQyVkdWWGxrUkVKWFRWWndlVmt3V25kWFIwVjRZMFJPV21FeVVrZGFWM2hIWTIxS1IxcEhiRmhTVlhCS1ZtMTBVMU14VlhoWFdHaFlZbXhhVmxsclpHOWpSbHB4VTIwNWJHSkhVbGxhVldNMVlWVXhjbUpFVWxkTmFsWlVWa2Q0YTFOR1ZuTlhiRlpYVFRGS05sWkhlR0ZXTWxKSVZXdG9hMUl5YUhCVmJHaENaREZhYzFwRVVtcE5WMUl3VlRKMGExZEhTbGhoUjBaVlZucFdkbFl3V25KbFJtUnlXa1prVjJFelFqWldhMlI2VFZaa1IxTnNXbXBTVjNoWVdXeG9RMVJHVW5KWGJFcHNVbTFTZWxsVldsTmhSVEZ6VTI1b1YxWjZSVEJhUkVaclVqSktTVlJ0YUZOaGVsWlFWa1phWVdReVZrZFdXR3hyVWtWS1dGUldXbmRsVm10M1YyNWtXRkl3VmpSWk1GSlBWMjFGZVZWclpHRldNMmhJV1RJeFMxSXhjRWhpUm1oVFZsaENTMVp0TVRCVk1VMTRWbGhvV0ZkSGFGbFpiWGhoVm14c2NscEhPV3BTYkhCNFZUSXdOV0pIU2toVmJHeGhWbGROTVZsV1ZYaGpiVXBGVld4a1RtRnNXbFZXYTJRMFlURk9SMVp1VGxoaVJscFlXV3RvUTFkV1draGxSMFpYVFd4S1NWWlhkRzloTVVwMFZXczVWMkZyV2t4Vk1uaHJWakZhZEZKdGNFNVdNVWwzVmxSS01HRXhaRWhUYkdob1VqQmFWbFp1Y0Zka2JGbDNWMjVLYkZKdFVubFhhMXByVmpKRmVsRnFXbGRoTWxJMlZGWmFXbVF3TVZkWGJXeHNZVEZ3V1ZkWGVHOVJNVkpIVlc1S1dHSkZjSE5WYlRGVFpXeHNWbGRzVG1oV2EzQXhWVmMxYjFZeFdYcGhTRXBYVmtWYWVsWnFSbGRqTVdSellVZHNWMVp1UWpaV01XUXdXVmRSZVZaclpGZFhSM2h5Vld0V1MxZEdVbGRYYm1Sc1ZteHNOVnBWYUd0WFIwcEhZMFpvV2sxSFVuWldNbmhoVjBaV2NscEhSbGRXTVVwUlZsZHdTMUl4U1hsU2EyaHBVbXMxY0ZsVVFuZE5iRnAwVFZSQ1ZrMVZNVFJXVm1oelZtMUZlVlZzV2xwaVdGSXpXVlZhVjJSSFZrWmtSM0JUWWtoQ05GWnJZM2RPVm1SSFYyNU9hbEp0ZUdGVVZWcFdUVlpzVjFaWWFHcGlWWEJHVmxkNGExUnRSbk5YYkZaWVZtMVJNRlY2Um1GamF6VlhZa1pLYVZKc2NGbFhWM1JoWkRGa1YxZHJhR3RTTUZwdlZGZHpNV1ZzV1hsT1ZrNW9UVlZzTlZsVmFFTldiVXBJWVVWT1lWSkZXbWhaZWtaM1VsWldkR05GTlZkTlZXd3pWbXhTUzAxSFJYaGFSV2hVWWtkb2IxVnFRbUZXYkZwMFpVaGtUazFXY0hsV01qRkhZV3hhY21ORVFtRlNWMUYzVm1wS1MyTnNUbkpoUm1SVFRUSm9iMVpyVWt0U01WbDRWRzVXVm1KRlNsaFZiRkpYVjFaYVIxbDZSbWxOVjFKSVdXdGFWMVZzWkVoaFJsSlZWbTFTVkZwWGVITldiR1J6Vkcxb1UxWkZXalpXVkVreFlqRlplRmRZY0ZaaVIyaFpWbTE0ZDFsV2NGWlhiWFJyVm10d2VsWnRNWE5XTVVsNllVUldWMDFYVVhkWFZtUlNaVlphY2xwR1pHbGlSWEI1VmxkMFYxTXlTWGhpUm14cVVsZFNjMVp0ZUV0bGJGcDBUVVJXV0ZJd2NFaFpNRnB2VjJzeFNHRkZlRmROYm1ob1ZqQmFWMk5zY0VoU2JHUk9UVzFvU2xZeFVrcGxSazE0VTFob2FsSlhVbWhWYlhNeFYwWlpkMVpyZEU1aVJuQXdXVEJXYTFkc1dYZFdhbEpYWWtkb2RsWXdXbXRUUjBaSFYyeHdhVmRIYUc5V2JURTBZekpPYzFwSVNtdFNNMEpVV1d0YWQwNUdXbGhOVkVKT1VteHNORll5TlU5aGJFcFlZVVpvVjJGck5WUldSVnB6VmxaR1dXRkdUbGRoTTBJMlZtdGtORmxXVlhsVGExcFlWMGhDV0Zac1duZFNNVkY0VjJ0T1ZtSkZTbFpVVlZGM1VGRTlQUT09'

for i in range(20):
    enc = enc.decode('base64')

print enc
★var4 = " RaziCTF"
package com.example.razictf_2;

public class a2 {
   private int fromHex(char var1) {
      if (var1 >= '0' && var1 <= '9') {
         return var1 - 48;
      } else {
         byte var2 = 65;
         if (var1 < 'A' || var1 > 'F') {
            var2 = 97;
            if (var1 < 'a' || var1 > 'f') {
               throw new IllegalArgumentException();
            }
         }

         return var1 - var2 + 10;
      }
   }

   private char toHex(int var1) {
      if (var1 >= 0 && var1 <= 15) {
         return "0123456789ABCDEF".charAt(var1);
      } else {
         throw new IllegalArgumentException();
      }
   }

   public String run(int var1) {
      return this.xorHex("787d6c7f2c352b2c", "313333376d616e73313333376861");
   }

   public String xorHex(String var1, String var2) {
      char[] var3 = new char[var1.length()];
      byte var4 = 0;

      int var5;
      for(var5 = 0; var5 < var3.length; ++var5) {
         var3[var5] = this.toHex(this.fromHex(var1.charAt(var5)) ^ this.fromHex(var2.charAt(var5)));
      }

      StringBuilder var6 = new StringBuilder();

      int var8;
      for(var5 = var4; var5 < (new String(var3)).length(); var5 = var8) {
         var2 = new String(var3);
         var8 = var5 + 2;
         var6.append((char)Integer.parseInt(var2.substring(var5, var8), 16));
      }

      StringBuilder var7 = new StringBuilder();
      var7.append("{");
      var7.append(var6.toString().trim());
      return var7.toString();
   }
}

上記を実行するだけでよい。

var1 = '787d6c7f2c352b2c'
var2 = '313333376d616e73313333376861'

var3 = ''
for i in range(len(var1)):
    var3 += hex(int(var1[i], 16) ^ int(var2[i], 16))[2:]

var6 = ''
for i in range(0, len(var3), 2):
    var6 += chr(int(var3[i:i+2], 16))

var7 = '{' + var6
print var7
★{IN_HATE_
 →var9 = " RaziCTF{IN_HATE_"
package com.example.razictf_2;

public class a3 {
   public String run(int var1) {
      var1 = var1 % 100000 / 2;
      StringBuilder var2 = new StringBuilder();
      var2.append(var1 - var1);
      var2.append("F");
      return var2.toString();
   }
}
★0F
 →var9 = " RaziCTF{IN_HATE_0F"
package com.example.razictf_2;

public class a4 {
   public String run(int var1) {
      return "_RUNN";
   }
}
★_RUNN
 →var4 = " RaziCTF{IN_HATE_0F_RUNN"
package com.example.razictf_2;

import java.security.MessageDigest;

public class a5 {
   public String run(int var1) {
      String[] var2 = new String[]{"!", "%", "="};
      String[] var3 = new String[]{"a", "b", "N"};
      String[] var4 = new String[]{"1", "G", "2"};
      String[] var5 = new String[]{"_", "%", "="};
      String var6 = "0";
      String[] var7 = new String[]{"C", "q", "3"};
      String[] var8 = new String[]{"4", "K", "("};
      String[] var9 = new String[]{"5", "J", "K"};
      System.out.println("a");

      String var12;
      for(var1 = 0; var1 < 3; ++var1) {
         for(int var10 = 0; var10 < 3; var6 = var12) {
            int var11 = 0;
            var12 = var6;

            String var48;
            String[] var49;
            for(var49 = var5; var11 < 3; var12 = var48) {
               int var13 = 0;

               String[] var52;
               for(var48 = var12; var13 < 3; var7 = var52) {
                  int var14 = 0;

                  for(var52 = var7; var14 < 3; var8 = var7) {
                     int var15 = 0;
                     var7 = var8;

                     for(var8 = var52; var15 < 3; ++var15) {
                        for(int var16 = 0; var16 < 3; ++var16) {
                           for(int var17 = 0; var17 < 3; var3 = var52) {
                              int var18 = 0;
                              var52 = var3;
                              String[] var19 = var2;

                              String[] var20;
                              for(var20 = var49; var18 < 3; var4 = var2) {
                                 StringBuilder var42 = new StringBuilder();
                                 var42.append(var19[var1]);
                                 var42.append(var52[var10]);
                                 var42.append(var4[var11]);
                                 var42.append(var20[var13]);
                                 var42.append((new String[]{"A", "L", "D"})[var14]);
                                 var42.append((new String[]{"R", "0", "$"})[var15]);
                                 var42.append(var8[var16]);
                                 var42.append(var7[var17]);
                                 var42.append(var9[var18]);
                                 String var43 = var42.toString();
                                 StringBuilder var40 = new StringBuilder();
                                 var40.append(var43);
                                 var40.append("}");
                                 String var21 = var40.toString();
                                 System.out.println(var21);

                                 String var47;
                                 label174: {
                                    boolean var28;
                                    label173: {
                                       Exception var50;
                                       label222: {
                                          Exception var10000;
                                          label170: {
                                             Exception var44;
                                             label169: {
                                                Exception var46;
                                                label213: {
                                                   byte[] var22;
                                                   StringBuilder var23;
                                                   int var24;
                                                   label167: {
                                                      label214: {
                                                         MessageDigest var45;
                                                         try {
                                                            var45 = MessageDigest.getInstance("MD5");
                                                         } catch (Exception var39) {
                                                            var44 = var39;
                                                            break label214;
                                                         }

                                                         try {
                                                            var45.update(var21.getBytes());
                                                            var22 = var45.digest();
                                                            var23 = new StringBuilder();
                                                         } catch (Exception var38) {
                                                            var44 = var38;
                                                            break label214;
                                                         }

                                                         try {
                                                            var24 = var22.length;
                                                            break label167;
                                                         } catch (Exception var37) {
                                                            var44 = var37;
                                                         }
                                                      }

                                                      var49 = var4;
                                                      var46 = var44;
                                                      break label213;
                                                   }

                                                   int var25 = 0;
                                                   var3 = var4;

                                                   label155:
                                                   while(true) {
                                                      boolean var10001;
                                                      if (var25 >= var24) {
                                                         var2 = var3;
                                                         var47 = var48;
                                                         var3 = var3;

                                                         try {
                                                            var28 = var23.toString().equals("b469f80f05290ed415770ea56e69a476");
                                                            break label173;
                                                         } catch (Exception var29) {
                                                            var10000 = var29;
                                                            var10001 = false;
                                                            break label170;
                                                         }
                                                      }

                                                      var49 = var3;
                                                      String var41 = var48;

                                                      label216: {
                                                         String var26;
                                                         try {
                                                            var26 = Integer.toHexString(var22[var25] & 255);
                                                         } catch (Exception var36) {
                                                            var10000 = var36;
                                                            var10001 = false;
                                                            break label216;
                                                         }

                                                         var47 = var48;
                                                         var5 = var3;

                                                         while(true) {
                                                            var49 = var5;
                                                            var41 = var47;

                                                            int var27;
                                                            try {
                                                               var27 = var26.length();
                                                            } catch (Exception var35) {
                                                               var10000 = var35;
                                                               var10001 = false;
                                                               break;
                                                            }

                                                            if (var27 >= 2) {
                                                               var41 = var47;
                                                               var47 = var47;
                                                               var3 = var5;

                                                               try {
                                                                  var23.append(var26);
                                                               } catch (Exception var30) {
                                                                  var10000 = var30;
                                                                  var10001 = false;
                                                                  break label170;
                                                               }

                                                               ++var25;
                                                               var3 = var5;
                                                               var48 = var41;
                                                               continue label155;
                                                            }

                                                            StringBuilder var51;
                                                            try {
                                                               var51 = new StringBuilder();
                                                            } catch (Exception var34) {
                                                               var44 = var34;
                                                               var6 = var47;
                                                               var2 = var5;
                                                               break label169;
                                                            }

                                                            var41 = var47;
                                                            var47 = var47;
                                                            var3 = var5;

                                                            try {
                                                               var51.append(var41);
                                                            } catch (Exception var33) {
                                                               var10000 = var33;
                                                               var10001 = false;
                                                               break label170;
                                                            }

                                                            var47 = var41;
                                                            var3 = var5;

                                                            try {
                                                               var51.append(var26);
                                                            } catch (Exception var32) {
                                                               var10000 = var32;
                                                               var10001 = false;
                                                               break label170;
                                                            }

                                                            var47 = var41;
                                                            var3 = var5;

                                                            try {
                                                               var26 = var51.toString();
                                                            } catch (Exception var31) {
                                                               var10000 = var31;
                                                               var10001 = false;
                                                               break label170;
                                                            }

                                                            var47 = var41;
                                                         }
                                                      }

                                                      var46 = var10000;
                                                      var48 = var41;
                                                      break;
                                                   }
                                                }

                                                var2 = var49;
                                                var6 = var48;
                                                var44 = var46;
                                             }

                                             var47 = var6;
                                             var50 = var44;
                                             break label222;
                                          }

                                          var50 = var10000;
                                          var2 = var3;
                                       }

                                       var50.printStackTrace();
                                       break label174;
                                    }

                                    var47 = var48;
                                    if (var28) {
                                       return var21;
                                    }
                                 }

                                 ++var18;
                                 var48 = var47;
                              }

                              ++var17;
                              var49 = var20;
                              var2 = var19;
                           }
                        }
                     }

                     ++var14;
                     var52 = var8;
                  }

                  ++var13;
               }

               ++var11;
            }

            ++var10;
            var5 = var49;
         }
      }

      return "y";
   }
}
★そのまま実行した方が早い→!NG_L0CK5}
 →var5 = " RaziCTF{IN_HATE_0F_RUNN!NG_L0CK5}"
RaziCTF{IN_HATE_0F_RUNN!NG_L0CK5}

Can you see thorough the crowd? (Digital forensics)

ncで接続し、適当な文字を入力すると、base64文字列が延々出力される。よく見ると、","と","の間にPNGBase64文字列が表示されることがわかる。
デコードすると、IHDRがRaziになっているので、その変換だけ行い、PNG画像にする。

import socket

def recvuntil(s, tails):
    data = ''
    while True:
        for tail in tails:
            if tail in data:
                return data
        data += s.recv(1)

s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(('130.185.122.69', 12478))

data = recvuntil(s, ':')
print data + 'a'
s.sendall('a\n')

data = recvuntil(s, ',')
data = recvuntil(s, ',')[:-1]

data = data.decode('base64')
data = data[:12] + 'IHDR' + data[16:]

with open('flag.png', 'wb') as f:
    f.write(data)

画像にはフラグが書かれていた。
f:id:satou-y:20201106123453p:plain

RAZICTF{CORRUPT3D_IM4G3S_ARE_L0V3LY}

Culture (Steganography)

$ zsteg enc.png
imagedata           .. text: "+*#QRM'(\""
b1,bgr,lsb,xy       .. text: "RaziCTF{i_s33_ur_4_MaN_0f_LSB_aS_W3LL}====="
b2,b,lsb,xy         .. text: "UZ_yl\t z"
b4,r,lsb,xy         .. text: "ff3\"\"#Ffffwwww"
b4,r,msb,xy         .. text: ["U" repeated 8 times]
b4,g,lsb,xy         .. text: "322\"3\"22TB2\""
b4,g,msb,xy         .. text: "UUUU3333"
b4,b,lsb,xy         .. text: "\"#33#\"33EDDDUUUU"
b4,b,msb,xy         .. text: ["U" repeated 8 times]
RaziCTF{i_s33_ur_4_MaN_0f_LSB_aS_W3LL}

Cliche (Steganography)

wavの画像受信データがあるかもしれないので、sstvのツールでデコードしてみる。

$ sstv -d enc.wav -o flag.png
[sstv] Searching for calibration header... Found!    
[sstv] Detected SSTV mode Scottie 1
[sstv] Decoding image...   [#############################################] 100%
[sstv] Drawing image data...
[sstv] ...Done!

flag.pngにフラグが書かれている。
f:id:satou-y:20201106123815p:plain

RaziCTF{h0w_y0u_d0in}

Mod Is Coming (Steganography)

f1は中国人余剰定理の結果を返す。f2は最大公約数を返す。f3はinverseを返す。
secretmsg.txtの長さは画像の高さから331バイト。kを総当たりして、条件を満たすものを探す。

from PIL import Image

def f1(n, a):
    sum = 0
    prod = reduce(lambda a, b: a*b, n)
    for n_i, a_i in zip(n, a):
        p = prod // n_i
        sum += a_i * f3(p, n_i) * p
    return sum % prod

def f2(a, b): 
    if b == 0: 
        return a 
    else: 
        return f2(b, a % b)

def f3(a, b):
    b0 = b
    x0, x1 = 0, 1
    if b == 1: return 1
    while a > 1:
        q = a // b
        a, b = b, a % b
        x0, x1 = x1 - q * x0, x0
    if x1 < 0: x1 += b0
    return x1

LEN = 331

c_p = []
for i in range(10, 21):
    for j in range(i+1, 21):
        if f2(i, j) == 1:
            c_p.append([i, j])

ks = []
for i in range(len(c_p)):
    k = f1(c_p[i], [LEN, LEN * 3])
    if k not in ks:
        ks.append(k)

img = Image.open('enc.png').convert('RGB')
r, g, b = img.getpixel((0, 0))

for k in ks:
    c1 = (f3(k-10, 251) * r) % 251
    c2 = (f3(k, 251) * g) % 251
    c3 = (f3(k+10, 251) * b) % 251
    if c1 == c2 and c2 == c3:
        print '[+] k =', k
        break

secretmsg = ''
for y in range(LEN):
    r, g, b = img.getpixel((0, y))
    c = (f3(k-10, 251) * r) % 251
    secretmsg += chr(c)

print secretmsg

実行結果は以下の通り。

[+] k = 201
Chaos isn't a pit. Chaos is a ladder, Many who try to climb it fail, and never get to try again, the fall breaks them. And some are given a chance to climb, but they refuse. They cling to the realm, or the gods, or love ... illusions. Only the ladder is real, the climb is all there is. RaziCTF{7h3_script_1s_d4rk_4nd_full_0f_m0ds}

末尾にフラグが書かれている。

RaziCTF{7h3_script_1s_d4rk_4nd_full_0f_m0ds}

Cryptfun (Cryptography)

substitution cipher symbolで調べたら、Betamaze alphabetであることがわかった。https://omniglot.com/conscripts/betamaze.htmを参考に復号する。

UC4NDRAWMAZ3SWITHITT00
RaziCTF{UC4NDRAWMAZ3SWITHITT00}

Ladder (Cryptography)

base32デコード、base58デコード、base62デコード、base64デコード、base85デコードの順にデコードする。

#!/usr/bin/python3
import base64
import base58
import base62
from Crypto.Util.number import *

with open('enc.txt', 'r') as f:
    data = f.read()

data = base64.b32decode(data)
print(data)

data = base58.b58decode(data)
print(data)

data = long_to_bytes(base62.decode(data.decode()))
print(data)

data = base64.b64decode(data)
print(data)

data = base64.a85decode(data)
print(data)

実行結果は以下の通り。

b'3ujJnYq1YPYVouAmFC24c36quqhmGkcm5LL5mZGvs6w4mewG9Cg3jLhWJgcdMyT1EM1ZYp2cCabt6syu9oAnjLeoDkiJKgS7'
b'B3ubcEe7waVuE55z96FTrO8JvfuevhFXEhXqzkWINOiIaRd4OlGLhL5jgqUXaQRwNC0CXl'
b'O0lPbGM2Vz9PJUc7RVNyMFFeWVlDaSFJIzg3Yy1wQDNkWE1JLw=='
b';IOlc6W?O%G;ESr0Q^YYCi!I#87c-p@3dXMI/'
b'RaziCTF{w3_G0t_4ll_tHe_Ba$3s}'
RaziCTF{w3_G0t_4ll_tHe_Ba$3s}

Cross Onion Roll!!! (Cryptography)

タイトルからCross=Xとして、頭文字をとって、XORと推測。XOR Crackerでクラックしてみる。XORキーは13バイトで、最初にフラグが入っていそう。調整しながら復号してみる。

with open('cipher', 'rb') as f:
    ct = f.read()

pre_flag = 'RaziCTF{d0nt_'

key = ''
for i in range(13):
    key += chr(ord(ct[i]) ^ ord(pre_flag[i]))

pt = ''
for i in range(len(ct)):
    pt += chr(ord(ct[i]) ^ ord(key[i%len(key)]))

print pt

復号結果は以下の通り。

RaziCTF{d0nt_r3pe4T_kEy_1N_X0R} You cannot be buried in obscurity , you are exposed upon a grand theater to the view of the world . If your actions are upright and benevolent , be assured they will augment your power and happiness.
RaziCTF{d0nt_r3pe4T_kEy_1N_X0R}

A rEal gAME (Cryptography)

Rail Fence Cipher。https://www.geocachingtoolbox.com/index.php?lang=en&page=railFenceCipherで復号する。

RratDLD{TED_4_O0VU_PA4LU_DCA_SRIAU_I1YH3$}

Bifid Cipher。https://www.geocachingtoolbox.com/index.php?lang=en&page=bifidCipherでkeyに"RaziCTF"を指定して復号する。

RaziCTF{ITS_4_G0OD_ST4RT_XTO_STUDY_C1PH3$}