├── settings.gradle ├── img └── 1.png ├── .gitattributes ├── gradle └── wrapper │ ├── gradle-wrapper.jar │ └── gradle-wrapper.properties ├── src └── burp │ ├── Config.java │ ├── json │ ├── SettingJson.kt │ └── PluginsJson.kt │ ├── BurpExtender.java │ ├── fuction │ ├── CodeMode.kt │ ├── PythonFunc.kt │ └── CoreFunc.kt │ └── ui │ ├── About.java │ ├── SettingConfig.java │ ├── AutoConvertRadix.java │ ├── PluginsConfig.java │ ├── MainUi.java │ └── DecodePanel.java ├── README.md ├── gradlew.bat ├── .gitignore ├── gradlew └── LICENSE /settings.gradle: -------------------------------------------------------------------------------- 1 | rootProject.name = 'DaE' 2 | 3 | -------------------------------------------------------------------------------- /img/1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/0Chencc/DaE/HEAD/img/1.png -------------------------------------------------------------------------------- /.gitattributes: -------------------------------------------------------------------------------- 1 | # Auto detect text files and perform LF normalization 2 | * text=auto 3 | -------------------------------------------------------------------------------- /gradle/wrapper/gradle-wrapper.jar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/0Chencc/DaE/HEAD/gradle/wrapper/gradle-wrapper.jar -------------------------------------------------------------------------------- /gradle/wrapper/gradle-wrapper.properties: -------------------------------------------------------------------------------- 1 | distributionBase=GRADLE_USER_HOME 2 | distributionPath=wrapper/dists 3 | distributionUrl=https\://services.gradle.org/distributions/gradle-6.7-bin.zip 4 | zipStoreBase=GRADLE_USER_HOME 5 | zipStorePath=wrapper/dists 6 | -------------------------------------------------------------------------------- /src/burp/Config.java: -------------------------------------------------------------------------------- 1 | package burp; 2 | 3 | import burp.fuction.PythonFunc; 4 | import burp.fuction.PythonFunc; 5 | 6 | import java.io.File; 7 | 8 | /** 9 | * @author linchen 10 | */ 11 | public class Config { 12 | public final static String VERSION = "1.1.3"; 13 | public final static String SLOGAN = ""; 14 | public final static String ABOUT = 15 | "Author:0chen(@0chencc)\n" + 16 | "Twitter:@0chencc\n" + 17 | "GitHub:https://github.com/0Chencc\n" + 18 | "Wechat Official Accounts(公众号):XizhouPoetry\n" + 19 | "Repository Url:https://github.com/0Chencc/CTFCrackTools\n" + 20 | "米斯特安全团队招CTF选手,有意向联系admin@hi-ourlife.com"; 21 | public final static File PLUGIN_FILE = new File("ctfcracktools_plugins.json"); 22 | public final static File SETTING_FILE = new File("ctfcracktools_setting.json"); 23 | 24 | public static PythonFunc pyFunc = new PythonFunc(); 25 | 26 | } 27 | -------------------------------------------------------------------------------- /src/burp/json/SettingJson.kt: -------------------------------------------------------------------------------- 1 | package burp.json 2 | 3 | import com.google.gson.Gson 4 | import com.google.gson.GsonBuilder 5 | import com.google.gson.reflect.TypeToken 6 | import burp.Config 7 | import java.io.* 8 | 9 | class SettingJson { 10 | init { 11 | if(!isJson()){ 12 | val initSetting = mapOf("jython" to "") 13 | Config.SETTING_FILE.createNewFile() 14 | writeJson(initSetting) 15 | } 16 | } 17 | 18 | /** 19 | * 返回一个储存配置信息的Map 20 | * @return Map 21 | */ 22 | fun parseJson():Map{ 23 | val settingReader = BufferedReader(FileReader(Config.SETTING_FILE)) 24 | return Gson().fromJson(settingReader, object : TypeToken>() {}.type) 25 | ?: return mapOf(pair = "jython" to "") 26 | } 27 | 28 | /** 29 | * 将配置信息写入json文件 30 | * @param Setting String 配置信息 31 | */ 32 | fun writeJson(setting:Map){ 33 | val gson = GsonBuilder().setPrettyPrinting().create() 34 | val writer = BufferedWriter(FileWriter(Config.SETTING_FILE)) 35 | writer.write(gson.toJson(setting)) 36 | writer.flush() 37 | } 38 | fun isJson():Boolean = Config.SETTING_FILE.isFile && Config.SETTING_FILE.exists() 39 | } -------------------------------------------------------------------------------- /src/burp/BurpExtender.java: -------------------------------------------------------------------------------- 1 | package burp; 2 | 3 | import javax.swing.*; 4 | import java.awt.*; 5 | import java.io.PrintWriter; 6 | 7 | import burp.ui.MainUi; 8 | 9 | /** 10 | * @author linchen 11 | */ 12 | public class BurpExtender implements IBurpExtender, ITab { 13 | private IBurpExtenderCallbacks callbacks; 14 | private static PrintWriter stdout; 15 | private final MainUi main = new MainUi(); 16 | @Override 17 | public void registerExtenderCallbacks(final IBurpExtenderCallbacks callbacks) 18 | { 19 | this.callbacks = callbacks; 20 | callbacks.setExtensionName(String.format("DaE (%s) - CTFCrackTools's Burpsuite Plugin - Decode and Encode", Config.VERSION)); 21 | // 定义输出 22 | stdout = new PrintWriter(callbacks.getStdout(), true); 23 | stdout.println("@Author: 0chencc"); 24 | stdout.println("@Github: github.com/0Chencc"); 25 | // UI 26 | SwingUtilities.invokeLater(this::initialize); 27 | } 28 | private void initialize(){ 29 | callbacks.customizeUiComponent(main); 30 | callbacks.addSuiteTab(BurpExtender.this); 31 | } 32 | @Override 33 | public String getTabCaption(){ 34 | return "DaE"; 35 | } 36 | 37 | @Override 38 | public Component getUiComponent() { 39 | return main; 40 | } 41 | 42 | 43 | } -------------------------------------------------------------------------------- /src/burp/fuction/CodeMode.kt: -------------------------------------------------------------------------------- 1 | package ctfcracktools.fuction 2 | 3 | class CodeMode { 4 | companion object{ 5 | const val CRYPTO_FENCE = "Fence" 6 | const val CRYPTO_CAESAR = "CaesarCode" 7 | const val CRYPTO_PIG = "PigCode" 8 | const val CRYPTO_ROT13 = "ROT13" 9 | const val CRYPTO_HEX_2_STRING = "Hex2String" 10 | const val CRYPTO_STRING_2_HEX = "String2Hex" 11 | const val CRYPTO_UNICODE_2_ASCII = "Unicode2Ascii" 12 | const val CRYPTO_ASCII_2_UNICODE = "Ascii2Unicode" 13 | const val CRYPTO_REVERSE = "Reverse" 14 | 15 | const val DECODE_MORSE = "MorseDecode" 16 | const val DECODE_BACON = "BaconDecode" 17 | const val DECODE_BASE64 = "Base64Decode" 18 | const val DECODE_BASE32 = "BASE32Decode" 19 | const val DECODE_URL = "UrlDecode" 20 | const val DECODE_UNICODE = "UnicodeDecode" 21 | const val DECODE_HTML = "HtmlDecode" 22 | const val DECODE_VIGENERE = "VigenereDeCode" 23 | 24 | const val ENCODE_MORSE = "MorseEncode" 25 | const val ENCODE_BACON = "BaconEncode" 26 | const val ENCODE_BASE64 = "Base64Encode" 27 | const val ENCODE_BASE32 = "Base32Encode" 28 | const val ENCODE_URL = "UrlEncode" 29 | const val ENCODE_UNICODE = "UnicodeEncode" 30 | const val ENCODE_HTML = "HtmlEncode" 31 | const val ENCODE_VIGENERE = "VigenereEnCode" 32 | } 33 | } -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # DaE - Decode and Encode 2 | [CTFCrackTools](https://github.com/Acmesec/CTFCrackTools) 's BurpSuite Plugin - Decode and Encode 3 | 4 | Many people suggested that I develop BurpSuite version, so I ported this tool to Burp 5 | 6 | [![License: GPL v3](https://img.shields.io/badge/License-GPL%20v3-blue.svg)](https://github.com/0Chencc/DaE/blob/main/LICENSE) 7 | [![language](https://img.shields.io/badge/Language-Java/Kotlin-orange.svg)](https://github.com/0Chencc/DaE/) 8 | # Support 9 | 10 | ***Decode/Encode as*** 11 | - MorseCode 12 | 13 | - BaconCode 14 | 15 | - Base64 16 | 17 | - Base32 18 | 19 | - URL 20 | 21 | - Unicode 22 | 23 | - HtmlCode 24 | 25 | - VigenereCode 26 | 27 | ...... 28 | 29 | ***Decrypt as*** 30 | 31 | - Fence 32 | 33 | - Casar 34 | 35 | - PigCode 36 | 37 | - Rot13 38 | 39 | - Hex2String 40 | 41 | - String2Hex 42 | 43 | - Unicode2Ascii 44 | 45 | - Ascii2Unicode 46 | 47 | - Reverse 48 | 49 | ...... 50 | 51 | ***Plugin*** 52 | 53 | You can write your own plug-in to import into this framework 54 | 55 | (Due to jython problems, python3 is not supported) 56 | 57 | Required method:*main*,*author_info* 58 | 59 | ```python 60 | #-*- coding:utf-8 -*- 61 | #demo 62 | def main(input,a,b,c): 63 | return a+b+c 64 | 65 | #authorinfo 66 | def author_info(): 67 | info = { 68 | "author":"0chen", 69 | "name":"test_version", 70 | "key":["a","b","c"], 71 | "describe":"plugin describe" 72 | } 73 | return info 74 | ``` 75 | 76 | 77 | 78 | # Usage 79 | 80 | ![](img/1.png) 81 | -------------------------------------------------------------------------------- /src/burp/ui/About.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Created by JFormDesigner on Thu Nov 25 23:37:10 CST 2021 3 | */ 4 | 5 | package burp.ui; 6 | 7 | import burp.Config; 8 | 9 | import java.awt.*; 10 | import javax.swing.*; 11 | 12 | /** 13 | * @author 0chencc 14 | */ 15 | public class About extends JPanel { 16 | public About() { 17 | initComponents(); 18 | } 19 | 20 | private void initComponents() { 21 | // JFormDesigner - Component initialization - DO NOT MODIFY //GEN-BEGIN:initComponents 22 | scrollPane1 = new JScrollPane(); 23 | textArea1 = new JTextArea(); 24 | 25 | //======== this ======== 26 | setLayout(new GridBagLayout()); 27 | ((GridBagLayout)getLayout()).columnWidths = new int[] {0, 0}; 28 | ((GridBagLayout)getLayout()).rowHeights = new int[] {0, 0}; 29 | ((GridBagLayout)getLayout()).columnWeights = new double[] {1.0, 1.0E-4}; 30 | ((GridBagLayout)getLayout()).rowWeights = new double[] {1.0, 1.0E-4}; 31 | 32 | //======== scrollPane1 ======== 33 | { 34 | 35 | //---- textArea1 ---- 36 | textArea1.setLineWrap(true); 37 | scrollPane1.setViewportView(textArea1); 38 | } 39 | add(scrollPane1, new GridBagConstraints(0, 0, 1, 1, 0.0, 0.0, 40 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 41 | new Insets(0, 0, 0, 0), 0, 0)); 42 | // JFormDesigner - End of component initialization //GEN-END:initComponents 43 | textArea1.setText(Config.ABOUT); 44 | } 45 | 46 | // JFormDesigner - Variables declaration - DO NOT MODIFY //GEN-BEGIN:variables 47 | private JScrollPane scrollPane1; 48 | private JTextArea textArea1; 49 | // JFormDesigner - End of variables declaration //GEN-END:variables 50 | } 51 | -------------------------------------------------------------------------------- /src/burp/json/PluginsJson.kt: -------------------------------------------------------------------------------- 1 | package org.ctfcracktools.json 2 | 3 | import com.google.gson.Gson 4 | import com.google.gson.GsonBuilder 5 | import com.google.gson.reflect.TypeToken 6 | import burp.Config 7 | import java.io.* 8 | import kotlin.collections.ArrayList 9 | 10 | class PluginsJson { 11 | /** 12 | * 初始化 13 | */ 14 | init{ 15 | if(!isJson()){ 16 | val initPlugins = arrayListOf>() 17 | Config.PLUGIN_FILE.createNewFile() 18 | writeJson(initPlugins) 19 | } 20 | } 21 | 22 | /** 23 | * 解析json文件 24 | * @return 返回一个Map的ArrayList插件列表 25 | */ 26 | fun parseJson(): ArrayList> { 27 | val pluginsReader = BufferedReader(FileReader(Config.PLUGIN_FILE)) 28 | return Gson().fromJson(pluginsReader, object : TypeToken>>() {}.type) 29 | } 30 | 31 | /** 32 | * 根据name去json文件中进行搜索,返回第一个 33 | * @param name String 插件名称 34 | */ 35 | fun search(name:String):Map{ 36 | val plugins = parseJson() 37 | var plugin:Map = HashMap() 38 | plugins.forEach { 39 | if(it["name"].toString() == name){ 40 | plugin = it 41 | } 42 | } 43 | return plugin 44 | } 45 | 46 | /** 47 | * 删除插件 48 | * @param plugin Map 传入一个plugin的信息,进行删除 49 | */ 50 | fun removePlugin(plugin:Map){ 51 | val plugins = parseJson() 52 | plugins.remove(plugin) 53 | writeJson(plugins) 54 | } 55 | 56 | /**写入配置文件 57 | * @param plugins ArrayList> 插件别表 58 | */ 59 | fun writeJson(plugins:ArrayList>){ 60 | val gson = GsonBuilder().setPrettyPrinting().create() 61 | val writer = BufferedWriter(FileWriter(Config.PLUGIN_FILE)) 62 | writer.write(gson.toJson(plugins)) 63 | writer.flush() 64 | } 65 | 66 | /** 67 | * 判断是否为配置文件 68 | * @return Boolean 69 | */ 70 | fun isJson():Boolean = Config.PLUGIN_FILE.isFile && Config.PLUGIN_FILE.exists() 71 | } -------------------------------------------------------------------------------- /src/burp/fuction/PythonFunc.kt: -------------------------------------------------------------------------------- 1 | package burp.fuction 2 | 3 | import burp.json.SettingJson 4 | import org.python.core.* 5 | import org.python.util.PythonInterpreter 6 | import java.util.* 7 | 8 | 9 | class PythonFunc { 10 | lateinit var interpreter:PythonInterpreter 11 | 12 | /** 13 | * 初始化 14 | */ 15 | init { 16 | jythonLoad() 17 | } 18 | 19 | /** 20 | * 加载jython 21 | */ 22 | private fun jythonLoad(){ 23 | val props = Properties() 24 | val setting = SettingJson().parseJson() 25 | props["python.home"] = setting["jython"] 26 | props["python.console.encoding"] = "utf-8" 27 | props["python.security.respectJavaAccessibility"] = "false" 28 | props["python.import.site"] = "false" 29 | val sysProps = System.getProperties() 30 | PythonInterpreter.initialize(sysProps,props, arrayOfNulls(0)) 31 | val sysS = Py.getSystemState() 32 | sysS.path.add(System.getProperty("user.dir") + "") 33 | interpreter = PythonInterpreter() 34 | } 35 | 36 | /** 37 | * 加载py脚本 38 | * @param file 文件名(含目录) 39 | */ 40 | fun loadFile(file:String)= interpreter.execfile(file) 41 | 42 | /** 43 | * 加载要调用的函数 44 | * @param interpreter PythonInterpreter 45 | * @param funcName 函数名 46 | */ 47 | fun loadPythonFunc(interpreter: PythonInterpreter, funcName: String): PyFunction = interpreter[funcName, PyFunction::class.java] 48 | 49 | /** 50 | * 执行python脚本(无参数) 51 | * @param function 配合loadPythonFunc将加载好文件目录、函数的解析成函数形式传入 52 | */ 53 | fun execFunc(function:PyFunction):Any?{ 54 | var pyObject:PyObject? = null 55 | try{ 56 | pyObject = function.__call__() 57 | }catch (e: PyException){ 58 | e.printStackTrace() 59 | } 60 | return pyObject!!.__tojava__(Any::class.java) 61 | } 62 | 63 | /** 64 | * 执行python脚本(含参数) 65 | * @param function 配合loadPythonFunc将加载好文件目录、函数的解析成函数形式传入 66 | * @param values 多参数 67 | */ 68 | fun execFuncOfArr(function: PyFunction,vararg values: String?): Any? { 69 | val strings = arrayOfNulls(values.size) 70 | for (i in strings.indices) { 71 | strings[i] = Py.newString(values[i]) 72 | } 73 | var pyObject: PyObject? = null 74 | try { 75 | pyObject = function.__call__(strings) 76 | } catch (e: PyException) { 77 | e.printStackTrace() 78 | } 79 | return pyObject!!.__tojava__(Any::class.java) 80 | } 81 | 82 | /** 83 | * 获取作者信息 84 | * @param file 文件地址 85 | * @return Map 返回一个含有作者信息的map 86 | */ 87 | fun getAuthorInfo(file:String):Map { 88 | loadFile(file) 89 | return execFunc(loadPythonFunc(interpreter,"author_info")) as Map} 90 | } -------------------------------------------------------------------------------- /gradlew.bat: -------------------------------------------------------------------------------- 1 | @rem 2 | @rem Copyright 2015 the original author or authors. 3 | @rem 4 | @rem Licensed under the Apache License, Version 2.0 (the "License"); 5 | @rem you may not use this file except in compliance with the License. 6 | @rem You may obtain a copy of the License at 7 | @rem 8 | @rem https://www.apache.org/licenses/LICENSE-2.0 9 | @rem 10 | @rem Unless required by applicable law or agreed to in writing, software 11 | @rem distributed under the License is distributed on an "AS IS" BASIS, 12 | @rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | @rem See the License for the specific language governing permissions and 14 | @rem limitations under the License. 15 | @rem 16 | 17 | @if "%DEBUG%" == "" @echo off 18 | @rem ########################################################################## 19 | @rem 20 | @rem Gradle startup script for Windows 21 | @rem 22 | @rem ########################################################################## 23 | 24 | @rem Set local scope for the variables with windows NT shell 25 | if "%OS%"=="Windows_NT" setlocal 26 | 27 | set DIRNAME=%~dp0 28 | if "%DIRNAME%" == "" set DIRNAME=. 29 | set APP_BASE_NAME=%~n0 30 | set APP_HOME=%DIRNAME% 31 | 32 | @rem Resolve any "." and ".." in APP_HOME to make it shorter. 33 | for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi 34 | 35 | @rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. 36 | set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m" 37 | 38 | @rem Find java.exe 39 | if defined JAVA_HOME goto findJavaFromJavaHome 40 | 41 | set JAVA_EXE=java.exe 42 | %JAVA_EXE% -version >NUL 2>&1 43 | if "%ERRORLEVEL%" == "0" goto execute 44 | 45 | echo. 46 | echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. 47 | echo. 48 | echo Please set the JAVA_HOME variable in your environment to match the 49 | echo location of your Java installation. 50 | 51 | goto fail 52 | 53 | :findJavaFromJavaHome 54 | set JAVA_HOME=%JAVA_HOME:"=% 55 | set JAVA_EXE=%JAVA_HOME%/bin/java.exe 56 | 57 | if exist "%JAVA_EXE%" goto execute 58 | 59 | echo. 60 | echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME% 61 | echo. 62 | echo Please set the JAVA_HOME variable in your environment to match the 63 | echo location of your Java installation. 64 | 65 | goto fail 66 | 67 | :execute 68 | @rem Setup the command line 69 | 70 | set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar 71 | 72 | 73 | @rem Execute Gradle 74 | "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %* 75 | 76 | :end 77 | @rem End local scope for the variables with windows NT shell 78 | if "%ERRORLEVEL%"=="0" goto mainEnd 79 | 80 | :fail 81 | rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of 82 | rem the _cmd.exe /c_ return code! 83 | if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1 84 | exit /b 1 85 | 86 | :mainEnd 87 | if "%OS%"=="Windows_NT" endlocal 88 | 89 | :omega 90 | -------------------------------------------------------------------------------- /src/burp/ui/SettingConfig.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Created by JFormDesigner on Thu Nov 25 23:55:20 CST 2021 3 | */ 4 | 5 | package burp.ui; 6 | 7 | import burp.json.SettingJson; 8 | import burp.json.SettingJson; 9 | 10 | import java.awt.*; 11 | import java.awt.event.*; 12 | import java.util.Map; 13 | import javax.swing.*; 14 | import javax.swing.filechooser.FileNameExtensionFilter; 15 | 16 | 17 | /** 18 | * @author 0chencc 19 | */ 20 | public class SettingConfig extends JPanel { 21 | public SettingConfig() { 22 | initComponents(); 23 | } 24 | 25 | private void jythonPathConfirmActionPerformed(ActionEvent e) { 26 | // TODO add your code here 27 | SettingJson json = new SettingJson(); 28 | Map setting = json.parseJson(); 29 | JFileChooser selectFile = new JFileChooser(); 30 | selectFile.setFileSelectionMode(JFileChooser.FILES_ONLY); 31 | FileNameExtensionFilter filter = new FileNameExtensionFilter("Jython Jar File (.jar)","jar"); 32 | selectFile.setFileFilter(filter); 33 | int selectFrame = selectFile.showDialog(new JLabel(),"Select"); 34 | if (selectFrame == JFileChooser.APPROVE_OPTION){ 35 | String jythonPath = selectFile.getSelectedFile().toString(); 36 | setting.put("jython",jythonPath); 37 | json.writeJson(setting); 38 | jythonPathTextField.setText(jythonPath); 39 | } 40 | } 41 | 42 | private void initComponents() { 43 | // JFormDesigner - Component initialization - DO NOT MODIFY //GEN-BEGIN:initComponents 44 | label1 = new JLabel(); 45 | jythonPathTextField = new JTextField(); 46 | jythonPathConfirm = new JButton(); 47 | 48 | //======== this ======== 49 | setLayout(new GridBagLayout()); 50 | ((GridBagLayout)getLayout()).columnWidths = new int[] {0, 0, 0, 0}; 51 | ((GridBagLayout)getLayout()).rowHeights = new int[] {0, 0, 0, 0}; 52 | ((GridBagLayout)getLayout()).columnWeights = new double[] {0.0, 1.0, 0.0, 1.0E-4}; 53 | ((GridBagLayout)getLayout()).rowWeights = new double[] {0.0, 0.0, 0.0, 1.0E-4}; 54 | 55 | //---- label1 ---- 56 | label1.setText("Jython-Standalone.jar Path:"); 57 | add(label1, new GridBagConstraints(0, 0, 1, 1, 0.0, 0.0, 58 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 59 | new Insets(0, 0, 5, 5), 0, 0)); 60 | add(jythonPathTextField, new GridBagConstraints(1, 0, 1, 1, 0.0, 0.0, 61 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 62 | new Insets(0, 0, 5, 5), 0, 0)); 63 | 64 | //---- jythonPathConfirm ---- 65 | jythonPathConfirm.setText("Select"); 66 | jythonPathConfirm.addActionListener(e -> jythonPathConfirmActionPerformed(e)); 67 | add(jythonPathConfirm, new GridBagConstraints(2, 0, 1, 1, 0.0, 0.0, 68 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 69 | new Insets(0, 0, 5, 0), 0, 0)); 70 | // JFormDesigner - End of component initialization //GEN-END:initComponents 71 | SettingJson json = new SettingJson(); 72 | jythonPathTextField.setText(json.parseJson().get("jython")); 73 | } 74 | 75 | // JFormDesigner - Variables declaration - DO NOT MODIFY //GEN-BEGIN:variables 76 | private JLabel label1; 77 | private JTextField jythonPathTextField; 78 | private JButton jythonPathConfirm; 79 | // JFormDesigner - End of variables declaration //GEN-END:variables 80 | } 81 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | 2 | # Created by https://www.toptal.com/developers/gitignore/api/macos,gradle,intellij+all 3 | # Edit at https://www.toptal.com/developers/gitignore?templates=macos,gradle,intellij+all 4 | 5 | ### Intellij+all ### 6 | # Covers JetBrains IDEs: IntelliJ, RubyMine, PhpStorm, AppCode, PyCharm, CLion, Android Studio, WebStorm and Rider 7 | # Reference: https://intellij-support.jetbrains.com/hc/en-us/articles/206544839 8 | 9 | # User-specific stuff 10 | .idea/**/workspace.xml 11 | .idea/**/tasks.xml 12 | .idea/**/usage.statistics.xml 13 | .idea/**/dictionaries 14 | .idea/**/shelf 15 | 16 | # AWS User-specific 17 | .idea/**/aws.xml 18 | 19 | # Generated files 20 | .idea/**/contentModel.xml 21 | 22 | # Sensitive or high-churn files 23 | .idea/**/dataSources/ 24 | .idea/**/dataSources.ids 25 | .idea/**/dataSources.local.xml 26 | .idea/**/sqlDataSources.xml 27 | .idea/**/dynamic.xml 28 | .idea/**/uiDesigner.xml 29 | .idea/**/dbnavigator.xml 30 | 31 | # Gradle 32 | .idea/**/gradle.xml 33 | .idea/**/libraries 34 | 35 | # Gradle and Maven with auto-import 36 | # When using Gradle or Maven with auto-import, you should exclude module files, 37 | # since they will be recreated, and may cause churn. Uncomment if using 38 | # auto-import. 39 | # .idea/artifacts 40 | # .idea/compiler.xml 41 | # .idea/jarRepositories.xml 42 | # .idea/modules.xml 43 | # .idea/*.iml 44 | # .idea/modules 45 | # *.iml 46 | # *.ipr 47 | 48 | # CMake 49 | cmake-build-*/ 50 | 51 | # Mongo Explorer plugin 52 | .idea/**/mongoSettings.xml 53 | 54 | # File-based project format 55 | *.iws 56 | 57 | # IntelliJ 58 | out/ 59 | 60 | # mpeltonen/sbt-idea plugin 61 | .idea_modules/ 62 | 63 | # JIRA plugin 64 | atlassian-ide-plugin.xml 65 | 66 | # Cursive Clojure plugin 67 | .idea/replstate.xml 68 | 69 | # Crashlytics plugin (for Android Studio and IntelliJ) 70 | com_crashlytics_export_strings.xml 71 | crashlytics.properties 72 | crashlytics-build.properties 73 | fabric.properties 74 | 75 | # Editor-based Rest Client 76 | .idea/httpRequests 77 | 78 | # Android studio 3.1+ serialized cache file 79 | .idea/caches/build_file_checksums.ser 80 | 81 | ### Intellij+all Patch ### 82 | # Ignores the whole .idea folder and all .iml files 83 | # See https://github.com/joeblau/gitignore.io/issues/186 and https://github.com/joeblau/gitignore.io/issues/360 84 | 85 | .idea/ 86 | 87 | # Reason: https://github.com/joeblau/gitignore.io/issues/186#issuecomment-249601023 88 | 89 | *.iml 90 | modules.xml 91 | .idea/misc.xml 92 | *.ipr 93 | 94 | # Sonarlint plugin 95 | .idea/sonarlint 96 | 97 | ### macOS ### 98 | # General 99 | .DS_Store 100 | .AppleDouble 101 | .LSOverride 102 | 103 | # Icon must end with two \r 104 | Icon 105 | 106 | 107 | # Thumbnails 108 | ._* 109 | 110 | # Files that might appear in the root of a volume 111 | .DocumentRevisions-V100 112 | .fseventsd 113 | .Spotlight-V100 114 | .TemporaryItems 115 | .Trashes 116 | .VolumeIcon.icns 117 | .com.apple.timemachine.donotpresent 118 | 119 | # Directories potentially created on remote AFP share 120 | .AppleDB 121 | .AppleDesktop 122 | Network Trash Folder 123 | Temporary Items 124 | .apdisk 125 | 126 | ### Gradle ### 127 | .gradle 128 | build/ 129 | 130 | # Ignore Gradle GUI config 131 | gradle-app.setting 132 | 133 | # Avoid ignoring Gradle wrapper jar file (.jar files are usually ignored) 134 | !gradle-wrapper.jar 135 | 136 | # Cache of project 137 | .gradletasknamecache 138 | 139 | # # Work around https://youtrack.jetbrains.com/issue/IDEA-116898 140 | # gradle/wrapper/gradle-wrapper.properties 141 | 142 | ### Gradle Patch ### 143 | **/build/ 144 | 145 | # Eclipse Gradle plugin generated files 146 | # Eclipse Core 147 | .project 148 | # JDT-specific (Eclipse Java Development Tools) 149 | .classpath 150 | 151 | # End of https://www.toptal.com/developers/gitignore/api/macos,gradle,intellij+all 152 | 153 | #Users 154 | test 155 | *.jfd -------------------------------------------------------------------------------- /gradlew: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env sh 2 | 3 | # 4 | # Copyright 2015 the original author or authors. 5 | # 6 | # Licensed under the Apache License, Version 2.0 (the "License"); 7 | # you may not use this file except in compliance with the License. 8 | # You may obtain a copy of the License at 9 | # 10 | # https://www.apache.org/licenses/LICENSE-2.0 11 | # 12 | # Unless required by applicable law or agreed to in writing, software 13 | # distributed under the License is distributed on an "AS IS" BASIS, 14 | # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 15 | # See the License for the specific language governing permissions and 16 | # limitations under the License. 17 | # 18 | 19 | ############################################################################## 20 | ## 21 | ## Gradle start up script for UN*X 22 | ## 23 | ############################################################################## 24 | 25 | # Attempt to set APP_HOME 26 | # Resolve links: $0 may be a link 27 | PRG="$0" 28 | # Need this for relative symlinks. 29 | while [ -h "$PRG" ] ; do 30 | ls=`ls -ld "$PRG"` 31 | link=`expr "$ls" : '.*-> \(.*\)$'` 32 | if expr "$link" : '/.*' > /dev/null; then 33 | PRG="$link" 34 | else 35 | PRG=`dirname "$PRG"`"/$link" 36 | fi 37 | done 38 | SAVED="`pwd`" 39 | cd "`dirname \"$PRG\"`/" >/dev/null 40 | APP_HOME="`pwd -P`" 41 | cd "$SAVED" >/dev/null 42 | 43 | APP_NAME="Gradle" 44 | APP_BASE_NAME=`basename "$0"` 45 | 46 | # Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. 47 | DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"' 48 | 49 | # Use the maximum available, or set MAX_FD != -1 to use that value. 50 | MAX_FD="maximum" 51 | 52 | warn () { 53 | echo "$*" 54 | } 55 | 56 | die () { 57 | echo 58 | echo "$*" 59 | echo 60 | exit 1 61 | } 62 | 63 | # OS specific support (must be 'true' or 'false'). 64 | cygwin=false 65 | msys=false 66 | darwin=false 67 | nonstop=false 68 | case "`uname`" in 69 | CYGWIN* ) 70 | cygwin=true 71 | ;; 72 | Darwin* ) 73 | darwin=true 74 | ;; 75 | MINGW* ) 76 | msys=true 77 | ;; 78 | NONSTOP* ) 79 | nonstop=true 80 | ;; 81 | esac 82 | 83 | CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar 84 | 85 | 86 | # Determine the Java command to use to start the JVM. 87 | if [ -n "$JAVA_HOME" ] ; then 88 | if [ -x "$JAVA_HOME/jre/sh/java" ] ; then 89 | # IBM's JDK on AIX uses strange locations for the executables 90 | JAVACMD="$JAVA_HOME/jre/sh/java" 91 | else 92 | JAVACMD="$JAVA_HOME/bin/java" 93 | fi 94 | if [ ! -x "$JAVACMD" ] ; then 95 | die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME 96 | 97 | Please set the JAVA_HOME variable in your environment to match the 98 | location of your Java installation." 99 | fi 100 | else 101 | JAVACMD="java" 102 | which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. 103 | 104 | Please set the JAVA_HOME variable in your environment to match the 105 | location of your Java installation." 106 | fi 107 | 108 | # Increase the maximum file descriptors if we can. 109 | if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then 110 | MAX_FD_LIMIT=`ulimit -H -n` 111 | if [ $? -eq 0 ] ; then 112 | if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then 113 | MAX_FD="$MAX_FD_LIMIT" 114 | fi 115 | ulimit -n $MAX_FD 116 | if [ $? -ne 0 ] ; then 117 | warn "Could not set maximum file descriptor limit: $MAX_FD" 118 | fi 119 | else 120 | warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT" 121 | fi 122 | fi 123 | 124 | # For Darwin, add options to specify how the application appears in the dock 125 | if $darwin; then 126 | GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\"" 127 | fi 128 | 129 | # For Cygwin or MSYS, switch paths to Windows format before running java 130 | if [ "$cygwin" = "true" -o "$msys" = "true" ] ; then 131 | APP_HOME=`cygpath --path --mixed "$APP_HOME"` 132 | CLASSPATH=`cygpath --path --mixed "$CLASSPATH"` 133 | 134 | JAVACMD=`cygpath --unix "$JAVACMD"` 135 | 136 | # We build the pattern for arguments to be converted via cygpath 137 | ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null` 138 | SEP="" 139 | for dir in $ROOTDIRSRAW ; do 140 | ROOTDIRS="$ROOTDIRS$SEP$dir" 141 | SEP="|" 142 | done 143 | OURCYGPATTERN="(^($ROOTDIRS))" 144 | # Add a user-defined pattern to the cygpath arguments 145 | if [ "$GRADLE_CYGPATTERN" != "" ] ; then 146 | OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)" 147 | fi 148 | # Now convert the arguments - kludge to limit ourselves to /bin/sh 149 | i=0 150 | for arg in "$@" ; do 151 | CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -` 152 | CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option 153 | 154 | if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition 155 | eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"` 156 | else 157 | eval `echo args$i`="\"$arg\"" 158 | fi 159 | i=`expr $i + 1` 160 | done 161 | case $i in 162 | 0) set -- ;; 163 | 1) set -- "$args0" ;; 164 | 2) set -- "$args0" "$args1" ;; 165 | 3) set -- "$args0" "$args1" "$args2" ;; 166 | 4) set -- "$args0" "$args1" "$args2" "$args3" ;; 167 | 5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;; 168 | 6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;; 169 | 7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;; 170 | 8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;; 171 | 9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;; 172 | esac 173 | fi 174 | 175 | # Escape application args 176 | save () { 177 | for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done 178 | echo " " 179 | } 180 | APP_ARGS=`save "$@"` 181 | 182 | # Collect all arguments for the java command, following the shell quoting and substitution rules 183 | eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS" 184 | 185 | exec "$JAVACMD" "$@" 186 | -------------------------------------------------------------------------------- /src/burp/ui/AutoConvertRadix.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Created by JFormDesigner on Thu Nov 25 16:47:22 CST 2021 3 | */ 4 | 5 | package burp.ui; 6 | 7 | import java.awt.*; 8 | import javax.swing.*; 9 | import javax.swing.event.DocumentEvent; 10 | import javax.swing.event.DocumentListener; 11 | import java.math.BigInteger; 12 | import java.util.HashMap; 13 | import java.util.Map; 14 | 15 | /** 16 | * @author 0chencc 17 | */ 18 | public class AutoConvertRadix extends JPanel { 19 | public AutoConvertRadix() { 20 | initComponents(); 21 | } 22 | public void characterChange(DocumentEvent e){ 23 | int selectRadix = inputRadix.getSelectedIndex(); 24 | Map radix = new HashMap(){{ 25 | put(0,2); 26 | put(1,8); 27 | put(2,10); 28 | put(3,16); 29 | }}; 30 | try { 31 | BigInteger input = new BigInteger(inputTextField.getText(), radix.get(selectRadix)); 32 | Convert(input); 33 | }catch (NumberFormatException e1){} 34 | } 35 | public void Convert(BigInteger input){ 36 | binaryTextField.setText(input.toString(2)); 37 | octTextField.setText(input.toString(8)); 38 | decTextField.setText(input.toString(10)); 39 | hexTextField.setText(input.toString(16)); 40 | try{ 41 | int diy = Integer.parseInt(diyRadix.getText()); 42 | diyRadixOutput.setText(input.toString(diy)); 43 | }catch (Exception e){} 44 | } 45 | private void initComponents() { 46 | // JFormDesigner - Component initialization - DO NOT MODIFY //GEN-BEGIN:initComponents 47 | inputRadix = new JComboBox<>(); 48 | inputTextField = new JTextField(); 49 | label1 = new JLabel(); 50 | binaryTextField = new JTextField(); 51 | label2 = new JLabel(); 52 | octTextField = new JTextField(); 53 | label3 = new JLabel(); 54 | decTextField = new JTextField(); 55 | label4 = new JLabel(); 56 | hexTextField = new JTextField(); 57 | label5 = new JLabel(); 58 | diyRadix = new JTextField(); 59 | diyRadixOutput = new JTextField(); 60 | 61 | //======== this ======== 62 | setLayout(new GridBagLayout()); 63 | ((GridBagLayout)getLayout()).columnWidths = new int[] {80, 0, 0}; 64 | ((GridBagLayout)getLayout()).rowHeights = new int[] {0, 0, 0, 0, 0, 0, 0, 0}; 65 | ((GridBagLayout)getLayout()).columnWeights = new double[] {0.0, 1.0, 1.0E-4}; 66 | ((GridBagLayout)getLayout()).rowWeights = new double[] {0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 1.0E-4}; 67 | 68 | //---- inputRadix ---- 69 | inputRadix.setModel(new DefaultComboBoxModel<>(new String[] { 70 | "Binary", 71 | "Octal", 72 | "Decimal", 73 | "Hex" 74 | })); 75 | add(inputRadix, new GridBagConstraints(0, 0, 1, 1, 0.0, 0.0, 76 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 77 | new Insets(10, 0, 5, 5), 0, 0)); 78 | add(inputTextField, new GridBagConstraints(1, 0, 1, 1, 0.0, 0.0, 79 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 80 | new Insets(10, 0, 5, 0), 0, 0)); 81 | 82 | //---- label1 ---- 83 | label1.setText("Binary:"); 84 | add(label1, new GridBagConstraints(0, 1, 1, 1, 0.0, 0.0, 85 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 86 | new Insets(0, 5, 5, 5), 0, 0)); 87 | add(binaryTextField, new GridBagConstraints(1, 1, 1, 1, 0.0, 0.0, 88 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 89 | new Insets(0, 0, 5, 0), 0, 0)); 90 | 91 | //---- label2 ---- 92 | label2.setText("Octal:"); 93 | add(label2, new GridBagConstraints(0, 2, 1, 1, 0.0, 0.0, 94 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 95 | new Insets(0, 5, 5, 5), 0, 0)); 96 | add(octTextField, new GridBagConstraints(1, 2, 1, 1, 0.0, 0.0, 97 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 98 | new Insets(0, 0, 5, 0), 0, 0)); 99 | 100 | //---- label3 ---- 101 | label3.setText("Decimal:"); 102 | add(label3, new GridBagConstraints(0, 3, 1, 1, 0.0, 0.0, 103 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 104 | new Insets(0, 5, 5, 5), 0, 0)); 105 | add(decTextField, new GridBagConstraints(1, 3, 1, 1, 0.0, 0.0, 106 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 107 | new Insets(0, 0, 5, 0), 0, 0)); 108 | 109 | //---- label4 ---- 110 | label4.setText("Hexadecimal:"); 111 | add(label4, new GridBagConstraints(0, 4, 1, 1, 0.0, 0.0, 112 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 113 | new Insets(0, 5, 5, 5), 0, 0)); 114 | add(hexTextField, new GridBagConstraints(1, 4, 1, 1, 0.0, 0.0, 115 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 116 | new Insets(0, 0, 5, 0), 0, 0)); 117 | 118 | //---- label5 ---- 119 | label5.setText("Input the radix you want to convert"); 120 | add(label5, new GridBagConstraints(0, 5, 2, 1, 0.0, 0.0, 121 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 122 | new Insets(0, 0, 5, 0), 0, 0)); 123 | add(diyRadix, new GridBagConstraints(0, 6, 1, 1, 0.0, 0.0, 124 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 125 | new Insets(0, 0, 0, 5), 0, 0)); 126 | add(diyRadixOutput, new GridBagConstraints(1, 6, 1, 1, 0.0, 0.0, 127 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 128 | new Insets(0, 0, 0, 0), 0, 0)); 129 | // JFormDesigner - End of component initialization //GEN-END:initComponents 130 | DocumentListener allTextFieldListener = new DocumentListener() { 131 | @Override 132 | public void insertUpdate(DocumentEvent e) {characterChange(e);} 133 | @Override 134 | public void removeUpdate(DocumentEvent e) {characterChange(e);} 135 | @Override 136 | public void changedUpdate(DocumentEvent e) {characterChange(e);} 137 | }; 138 | inputTextField.getDocument().addDocumentListener(allTextFieldListener); 139 | } 140 | 141 | // JFormDesigner - Variables declaration - DO NOT MODIFY //GEN-BEGIN:variables 142 | private JComboBox inputRadix; 143 | private JTextField inputTextField; 144 | private JLabel label1; 145 | private JTextField binaryTextField; 146 | private JLabel label2; 147 | private JTextField octTextField; 148 | private JLabel label3; 149 | private JTextField decTextField; 150 | private JLabel label4; 151 | private JTextField hexTextField; 152 | private JLabel label5; 153 | private JTextField diyRadix; 154 | private JTextField diyRadixOutput; 155 | // JFormDesigner - End of variables declaration //GEN-END:variables 156 | } 157 | -------------------------------------------------------------------------------- /src/burp/ui/PluginsConfig.java: -------------------------------------------------------------------------------- 1 | package burp.ui;/* 2 | * Created by JFormDesigner on Thu Nov 25 11:35:29 CST 2021 3 | */ 4 | 5 | import java.awt.*; 6 | import java.awt.event.*; 7 | import java.util.ArrayList; 8 | import java.util.Map; 9 | import java.util.Vector; 10 | import javax.swing.*; 11 | import javax.swing.filechooser.FileNameExtensionFilter; 12 | import javax.swing.table.DefaultTableModel; 13 | 14 | import burp.Config; 15 | import org.ctfcracktools.json.PluginsJson; 16 | 17 | /** 18 | * @author 0chencc 19 | */ 20 | public class PluginsConfig extends JPanel { 21 | public PluginsConfig() { 22 | initComponents(); 23 | } 24 | 25 | private void removePluginActionPerformed(ActionEvent e) { 26 | // TODO add your code here 27 | PluginsJson json = new PluginsJson(); 28 | String t = pluginsList.getSelectedValue().toString(); 29 | Map plugin = json.search(t); 30 | json.removePlugin(plugin); 31 | name.remove(t); 32 | pluginsList.setListData(name); 33 | } 34 | 35 | private void addPluginActionPerformed(ActionEvent e) { 36 | // TODO add your code here 37 | PluginsJson json = new PluginsJson(); 38 | ArrayList> plugins = json.parseJson(); 39 | JFileChooser selectFile = new JFileChooser(); 40 | selectFile.setFileSelectionMode(JFileChooser.FILES_ONLY); 41 | FileNameExtensionFilter filter = new FileNameExtensionFilter("Plugin File (.py)","py"); 42 | selectFile.setFileFilter(filter); 43 | int selectFrame = selectFile.showDialog(new JLabel(),"Select"); 44 | if (selectFrame == JFileChooser.APPROVE_OPTION){ 45 | String pluginPath = selectFile.getSelectedFile().toString(); 46 | Map plugin = Config.pyFunc.getAuthorInfo(pluginPath); 47 | plugin.put("path",pluginPath); 48 | plugins.add(plugin); 49 | json.writeJson(plugins); 50 | name.add(plugin.get("name").toString()); 51 | pluginsList.setListData(name); 52 | } 53 | } 54 | 55 | private void pluginsListMouseClicked(MouseEvent e) { 56 | // TODO add your code here 57 | DefaultTableModel model = new DefaultTableModel(); 58 | PluginsJson json = new PluginsJson(); 59 | Map plugin = json.search(pluginsList.getSelectedValue().toString()); 60 | detailTable.setModel(model); 61 | Vector> detail = new Vector<>(); 62 | for(Map.Entry i :plugin.entrySet()){ 63 | Vector item = new Vector<>(); 64 | item.add(i.getKey()); 65 | item.add(i.getValue()); 66 | detail.add(item); 67 | } 68 | Vector title = new Vector<>(); 69 | title.add("Item"); 70 | title.add("Detail"); 71 | model.setDataVector(detail,title); 72 | } 73 | 74 | private void initComponents() { 75 | // JFormDesigner - Component initialization - DO NOT MODIFY //GEN-BEGIN:initComponents 76 | label1 = new JLabel(); 77 | addPlugin = new JButton(); 78 | scrollPane3 = new JScrollPane(); 79 | pluginsList = new JList(); 80 | removePlugin = new JButton(); 81 | label2 = new JLabel(); 82 | scrollPane1 = new JScrollPane(); 83 | detailTable = new JTable(); 84 | 85 | //======== this ======== 86 | setLayout(new GridBagLayout()); 87 | ((GridBagLayout)getLayout()).columnWidths = new int[] {55, 0, 0}; 88 | ((GridBagLayout)getLayout()).rowHeights = new int[] {0, 0, 0, 49, 0, 32, 0}; 89 | ((GridBagLayout)getLayout()).columnWeights = new double[] {0.0, 1.0, 1.0E-4}; 90 | ((GridBagLayout)getLayout()).rowWeights = new double[] {0.0, 0.0, 0.0, 0.0, 0.0, 1.0, 1.0E-4}; 91 | 92 | //---- label1 ---- 93 | label1.setText("Plugins"); 94 | add(label1, new GridBagConstraints(0, 0, 2, 1, 0.0, 0.0, 95 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 96 | new Insets(0, 0, 5, 0), 0, 0)); 97 | 98 | //---- addPlugin ---- 99 | addPlugin.setText("add"); 100 | addPlugin.addActionListener(e -> addPluginActionPerformed(e)); 101 | add(addPlugin, new GridBagConstraints(0, 1, 1, 1, 0.0, 0.0, 102 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 103 | new Insets(0, 0, 5, 5), 0, 0)); 104 | 105 | //======== scrollPane3 ======== 106 | { 107 | 108 | //---- pluginsList ---- 109 | pluginsList.addMouseListener(new MouseAdapter() { 110 | @Override 111 | public void mouseClicked(MouseEvent e) { 112 | pluginsListMouseClicked(e); 113 | } 114 | }); 115 | scrollPane3.setViewportView(pluginsList); 116 | } 117 | add(scrollPane3, new GridBagConstraints(1, 1, 1, 3, 0.0, 0.0, 118 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 119 | new Insets(0, 0, 5, 0), 0, 0)); 120 | 121 | //---- removePlugin ---- 122 | removePlugin.setText("remove"); 123 | removePlugin.addActionListener(e -> removePluginActionPerformed(e)); 124 | add(removePlugin, new GridBagConstraints(0, 2, 1, 1, 0.0, 0.0, 125 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 126 | new Insets(0, 0, 5, 5), 0, 0)); 127 | 128 | //---- label2 ---- 129 | label2.setText("Plugin Detail"); 130 | add(label2, new GridBagConstraints(0, 4, 2, 1, 0.0, 0.0, 131 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 132 | new Insets(0, 0, 5, 0), 0, 0)); 133 | 134 | //======== scrollPane1 ======== 135 | { 136 | 137 | //---- detailTable ---- 138 | detailTable.setModel(new DefaultTableModel( 139 | new Object[][] { 140 | {null, null}, 141 | {null, null}, 142 | }, 143 | new String[] { 144 | "Item", "Detail" 145 | } 146 | )); 147 | scrollPane1.setViewportView(detailTable); 148 | } 149 | add(scrollPane1, new GridBagConstraints(0, 5, 2, 1, 0.0, 0.0, 150 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 151 | new Insets(0, 0, 0, 0), 0, 0)); 152 | // JFormDesigner - End of component initialization //GEN-END:initComponents 153 | PluginsJson json = new PluginsJson(); 154 | ArrayList> plugins = json.parseJson(); 155 | name = new Vector<>(); 156 | for(Map i:plugins){ 157 | name.add(i.get("name").toString()); 158 | } 159 | pluginsList.setListData(name); 160 | } 161 | 162 | // JFormDesigner - Variables declaration - DO NOT MODIFY //GEN-BEGIN:variables 163 | private JLabel label1; 164 | private JButton addPlugin; 165 | private JScrollPane scrollPane3; 166 | private JList pluginsList; 167 | private JButton removePlugin; 168 | private JLabel label2; 169 | private JScrollPane scrollPane1; 170 | private JTable detailTable; 171 | // JFormDesigner - End of variables declaration //GEN-END:variables 172 | private Vector name; 173 | }; 174 | 175 | -------------------------------------------------------------------------------- /src/burp/ui/MainUi.java: -------------------------------------------------------------------------------- 1 | package burp.ui; 2 | 3 | import java.awt.*; 4 | import java.awt.event.*; 5 | import javax.swing.*; 6 | import javax.swing.event.ChangeEvent; 7 | import javax.swing.event.ChangeListener; 8 | import javax.swing.event.DocumentEvent; 9 | import javax.swing.event.DocumentListener; 10 | /* 11 | * Created by JFormDesigner on Wed Nov 24 18:42:26 CST 2021 12 | */ 13 | 14 | 15 | 16 | /** 17 | * @author 0chencc 18 | */ 19 | public class MainUi extends JPanel { 20 | public MainUi() { 21 | initComponents(); 22 | } 23 | public void closeTabActionPerformed(ActionEvent e){ 24 | if (tabbedPane2.getTabCount()>2){ 25 | if (tabbedPane2.getSelectedIndex()!=0){ 26 | tabbedPane2.remove(tabbedPane2.getSelectedIndex()); 27 | tabbedPane2.setSelectedIndex(tabbedPane2.getSelectedIndex()-1); 28 | }else{ 29 | tabbedPane2.remove(tabbedPane2.getSelectedIndex()); 30 | tabbedPane2.setSelectedIndex(tabbedPane2.getSelectedIndex()); 31 | } 32 | } 33 | } 34 | private void initComponents() { 35 | // JFormDesigner - Component initialization - DO NOT MODIFY //GEN-BEGIN:initComponents 36 | tabbedPane1 = new JTabbedPane(); 37 | tabbedPane2 = new JTabbedPane(); 38 | decodePanel1 = new DecodePanel(); 39 | decodePanel2 = new DecodePanel(); 40 | autoConvertRadix1 = new AutoConvertRadix(); 41 | pluginsConfig1 = new PluginsConfig(); 42 | settingConfig1 = new SettingConfig(); 43 | about1 = new About(); 44 | 45 | //======== this ======== 46 | setLayout(new GridBagLayout()); 47 | ((GridBagLayout)getLayout()).columnWidths = new int[] {0, 0}; 48 | ((GridBagLayout)getLayout()).rowHeights = new int[] {0, 0}; 49 | ((GridBagLayout)getLayout()).columnWeights = new double[] {1.0, 1.0E-4}; 50 | ((GridBagLayout)getLayout()).rowWeights = new double[] {1.0, 1.0E-4}; 51 | 52 | //======== tabbedPane1 ======== 53 | { 54 | 55 | //======== tabbedPane2 ======== 56 | { 57 | tabbedPane2.addTab("1", decodePanel1); 58 | tabbedPane2.addTab("...", decodePanel2); 59 | } 60 | tabbedPane1.addTab("DaE", tabbedPane2); 61 | tabbedPane1.addTab("RadiexConvert", autoConvertRadix1); 62 | tabbedPane1.addTab("PluginsConfig", pluginsConfig1); 63 | tabbedPane1.addTab("SettingConfig", settingConfig1); 64 | tabbedPane1.addTab("About", about1); 65 | } 66 | add(tabbedPane1, new GridBagConstraints(0, 0, 1, 1, 0.0, 0.0, 67 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 68 | new Insets(0, 0, 0, 0), 0, 0)); 69 | // JFormDesigner - End of component initialization //GEN-END:initComponents 70 | tabSwitch = new TabTitleEditListener(tabbedPane2); 71 | tabbedPane2.addChangeListener(tabSwitch); 72 | tabbedPane2.addMouseListener(tabSwitch); 73 | closeTab.addActionListener(e -> closeTabActionPerformed(e)); 74 | tabMenu.add(closeTab); 75 | } 76 | 77 | // JFormDesigner - Variables declaration - DO NOT MODIFY //GEN-BEGIN:variables 78 | private JTabbedPane tabbedPane1; 79 | private JTabbedPane tabbedPane2; 80 | private DecodePanel decodePanel1; 81 | private DecodePanel decodePanel2; 82 | private AutoConvertRadix autoConvertRadix1; 83 | private PluginsConfig pluginsConfig1; 84 | private SettingConfig settingConfig1; 85 | private About about1; 86 | // JFormDesigner - End of variables declaration //GEN-END:variables 87 | protected static JPopupMenu tabMenu = new JPopupMenu(); 88 | private JMenuItem closeTab = new JMenuItem("Delete"); 89 | private TabTitleEditListener tabSwitch; 90 | } 91 | class TabTitleEditListener extends MouseAdapter implements ChangeListener, DocumentListener { 92 | protected final JTextField editor = new JTextField(); 93 | protected final JTabbedPane tabbedPane; 94 | protected int editingIdx = -1; 95 | protected int len = -1; 96 | protected Boolean listen = true; 97 | protected Dimension dim; 98 | protected Component tabComponent; 99 | protected Boolean isRenameOk = false; 100 | protected final Action startEditing = new AbstractAction() { 101 | @Override public void actionPerformed(ActionEvent e) { 102 | editingIdx = tabbedPane.getSelectedIndex(); 103 | tabComponent = tabbedPane.getTabComponentAt(editingIdx); 104 | tabbedPane.setTabComponentAt(editingIdx, editor); 105 | isRenameOk = true; 106 | editor.setVisible(true); 107 | editor.setText(tabbedPane.getTitleAt(editingIdx)); 108 | editor.selectAll(); 109 | editor.requestFocusInWindow(); 110 | len = editor.getText().length(); 111 | dim = editor.getPreferredSize(); 112 | editor.setMinimumSize(dim); 113 | } 114 | }; 115 | protected final Action renameTabTitle = new AbstractAction() { 116 | @Override public void actionPerformed(ActionEvent e) { 117 | String title = editor.getText().trim(); 118 | if (editingIdx >= 0 && !title.isEmpty()) { 119 | String oldName = tabbedPane.getTitleAt(editingIdx); 120 | tabbedPane.setTitleAt(editingIdx, title); 121 | } 122 | cancelEditing.actionPerformed(null); 123 | } 124 | }; 125 | protected final Action cancelEditing = new AbstractAction() { 126 | @Override public void actionPerformed(ActionEvent e) { 127 | if (editingIdx >= 0) { 128 | tabbedPane.setTabComponentAt(editingIdx, tabComponent); 129 | editor.setVisible(false); 130 | editingIdx = -1; 131 | len = -1; 132 | tabComponent = null; 133 | editor.setPreferredSize(null); 134 | tabbedPane.requestFocusInWindow(); 135 | } 136 | } 137 | }; 138 | 139 | protected TabTitleEditListener(JTabbedPane tabbedPane) { 140 | super(); 141 | this.tabbedPane = tabbedPane; 142 | editor.setBorder(BorderFactory.createEmptyBorder()); 143 | editor.addFocusListener(new FocusAdapter() { 144 | @Override public void focusLost(FocusEvent e) { 145 | renameTabTitle.actionPerformed(null); 146 | } 147 | }); 148 | InputMap im = editor.getInputMap(JComponent.WHEN_FOCUSED); 149 | ActionMap am = editor.getActionMap(); 150 | im.put(KeyStroke.getKeyStroke(KeyEvent.VK_ESCAPE, 0), "cancel-editing"); 151 | am.put("cancel-editing", cancelEditing); 152 | im.put(KeyStroke.getKeyStroke(KeyEvent.VK_ENTER, 0), "rename-tab-title"); 153 | am.put("rename-tab-title", renameTabTitle); 154 | editor.getDocument().addDocumentListener(this); 155 | tabbedPane.getInputMap(JComponent.WHEN_FOCUSED).put(KeyStroke.getKeyStroke(KeyEvent.VK_ENTER, 0), "start-editing"); 156 | tabbedPane.getActionMap().put("start-editing", startEditing); 157 | } 158 | @Override public void stateChanged(ChangeEvent e) { 159 | if (e.getSource() instanceof JTabbedPane && listen) { 160 | JTabbedPane pane = (JTabbedPane) e.getSource(); 161 | if (!isRenameOk){ 162 | if (pane.getSelectedIndex() == pane.getComponentCount()-1){ 163 | newTab(); 164 | } 165 | }else{ 166 | if (pane.getSelectedIndex() == pane.getComponentCount()-2){ 167 | newTab(); 168 | } 169 | } 170 | } 171 | renameTabTitle.actionPerformed(null); 172 | } 173 | public void newTab(){ 174 | insertTab(tabbedPane); 175 | } 176 | public void insertTab(JTabbedPane pane){ 177 | pane.addTab(String.valueOf(pane.getTabCount()),new DecodePanel()); 178 | pane.remove(pane.getSelectedIndex()); 179 | pane.addTab("...",new JLabel()); 180 | } 181 | public void setListen(Boolean listen){ 182 | this.listen = listen; 183 | } 184 | @Override public void insertUpdate(DocumentEvent e) { 185 | updateTabSize(); 186 | } 187 | 188 | @Override public void removeUpdate(DocumentEvent e) { 189 | updateTabSize(); 190 | } 191 | 192 | @Override public void changedUpdate(DocumentEvent e) {} 193 | 194 | @Override public void mouseClicked(MouseEvent e) { 195 | switch (e.getButton()){ 196 | case 1: 197 | { 198 | Rectangle r = tabbedPane.getBoundsAt(tabbedPane.getSelectedIndex()); 199 | boolean isDoubleClick = e.getClickCount() >= 2; 200 | if (isDoubleClick && r.contains(e.getPoint())) { 201 | startEditing.actionPerformed(null); 202 | } else { 203 | renameTabTitle.actionPerformed(null); 204 | } 205 | break; 206 | } 207 | case 3:{ 208 | MainUi.tabMenu.show(e.getComponent(),e.getX(),e.getY()); 209 | break; 210 | } 211 | default: 212 | break; 213 | } 214 | } 215 | 216 | protected void updateTabSize() { 217 | editor.setPreferredSize(editor.getText().length() > len ? null : dim); 218 | tabbedPane.revalidate(); 219 | } 220 | } -------------------------------------------------------------------------------- /src/burp/ui/DecodePanel.java: -------------------------------------------------------------------------------- 1 | package burp.ui;/* 2 | * Created by JFormDesigner on Thu Nov 25 10:28:49 CST 2021 3 | */ 4 | 5 | import burp.Config; 6 | import ctfcracktools.fuction.CodeMode; 7 | import org.ctfcracktools.fuction.CoreFunc; 8 | import org.ctfcracktools.json.PluginsJson; 9 | 10 | import java.awt.*; 11 | import java.awt.event.*; 12 | import java.util.ArrayList; 13 | import java.util.Map; 14 | import javax.swing.*; 15 | import javax.swing.event.DocumentEvent; 16 | import javax.swing.event.DocumentListener; 17 | 18 | /** 19 | * @author 0chencc 20 | */ 21 | public class DecodePanel extends JPanel { 22 | public DecodePanel() { 23 | initComponents(); 24 | } 25 | public void inputCharacterChange(DocumentEvent e){ 26 | input = inputArea.getText(); 27 | int length = inputArea.getText().replace("\r|\n","").length(); 28 | inputCharacterCount.setText("InputArea - Now Input Character Count:"+length); 29 | } 30 | public void resultCharacterChange(DocumentEvent e){ 31 | input = inputArea.getText(); 32 | int length = resultArea.getText().replace("\r|\n","").length(); 33 | resultCharacterCount.setText("ResultArea - Now Result Character Count:"+length); 34 | } 35 | private void pluginsComboBoxActionPerformed(ActionEvent e) { 36 | // TODO add your code here 37 | if (pluginsComboBox.getSelectedIndex()==0){ 38 | return; 39 | } 40 | String select = pluginsComboBox.getItemAt(pluginsComboBox.getSelectedIndex()); 41 | 42 | Map plugin = json.search(select); 43 | String[] prams = {}; 44 | ArrayList keys = new ArrayList<>(); 45 | if (plugin.containsKey("key")){ 46 | keys = (ArrayList) plugin.get("key"); 47 | prams = new String[keys.size()+1]; 48 | } 49 | Config.pyFunc.loadFile(plugin.get("path").toString()); 50 | if (keys.size()>=1){ 51 | prams[0] = inputArea.getText(); 52 | for (int i = 1;i(name); 69 | pluginsComboBox.setModel(model); 70 | } 71 | private void reloadPluginsActionPerformed(ActionEvent e) { 72 | // TODO add your code here 73 | loadPlugin(); 74 | } 75 | 76 | private void encodeComboBoxActionPerformed(ActionEvent e) { 77 | // TODO add your code here 78 | if(encodeComboBox.getSelectedIndex()==0){ 79 | return; 80 | } 81 | String select = encodeComboBox.getItemAt(encodeComboBox.getSelectedIndex()); 82 | resultArea.setText(func.callFunc(input,select)); 83 | encodeComboBox.setSelectedIndex(0); 84 | } 85 | 86 | private void decodeComboBoxActionPerformed(ActionEvent e) { 87 | // TODO add your code here 88 | if (decodeComboBox.getSelectedIndex()==0){ 89 | return; 90 | } 91 | String select = decodeComboBox.getItemAt(decodeComboBox.getSelectedIndex()); 92 | resultArea.setText(func.callFunc(input,select)); 93 | decodeComboBox.setSelectedIndex(0); 94 | } 95 | 96 | private void decryptComboBoxActionPerformed(ActionEvent e) { 97 | // TODO add your code here 98 | if (decryptComboBox.getSelectedIndex()==0){ 99 | return; 100 | } 101 | String select = decryptComboBox.getItemAt(decryptComboBox.getSelectedIndex()); 102 | resultArea.setText(func.callFunc(input,select)); 103 | decryptComboBox.setSelectedIndex(0); 104 | } 105 | 106 | private void decodeComboBoxItemStateChanged(ItemEvent e) { 107 | // TODO add your code here 108 | } 109 | private void initComponents() { 110 | // JFormDesigner - Component initialization - DO NOT MODIFY //GEN-BEGIN:initComponents 111 | inputCharacterCount = new JLabel(); 112 | scrollPane1 = new JScrollPane(); 113 | inputArea = new JTextArea(); 114 | encodeComboBox = new JComboBox<>(); 115 | decodeComboBox = new JComboBox<>(); 116 | decryptComboBox = new JComboBox<>(); 117 | pluginsComboBox = new JComboBox<>(); 118 | reloadPlugins = new JButton(); 119 | resultCharacterCount = new JLabel(); 120 | scrollPane2 = new JScrollPane(); 121 | resultArea = new JTextArea(); 122 | 123 | //======== this ======== 124 | setLayout(new GridBagLayout()); 125 | ((GridBagLayout)getLayout()).columnWidths = new int[] {0, 0, 0, 0, 0, 0, 0, 0}; 126 | ((GridBagLayout)getLayout()).rowHeights = new int[] {0, 0, 0, 0, 0, 0}; 127 | ((GridBagLayout)getLayout()).columnWeights = new double[] {0.4, 0.0, 0.0, 0.0, 0.0, 0.0, 0.4, 1.0E-4}; 128 | ((GridBagLayout)getLayout()).rowWeights = new double[] {0.0, 1.0, 0.0, 0.0, 1.0, 1.0E-4}; 129 | 130 | //---- inputCharacterCount ---- 131 | inputCharacterCount.setText("InputArea - Now Input Character Count:0"); 132 | add(inputCharacterCount, new GridBagConstraints(0, 0, 7, 1, 0.0, 0.0, 133 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 134 | new Insets(0, 0, 5, 0), 0, 0)); 135 | 136 | //======== scrollPane1 ======== 137 | { 138 | 139 | //---- inputArea ---- 140 | inputArea.setLineWrap(true); 141 | scrollPane1.setViewportView(inputArea); 142 | } 143 | add(scrollPane1, new GridBagConstraints(0, 1, 7, 1, 0.0, 0.0, 144 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 145 | new Insets(0, 0, 5, 0), 0, 0)); 146 | 147 | //---- encodeComboBox ---- 148 | encodeComboBox.setModel(new DefaultComboBoxModel<>(new String[] { 149 | "Encode as" 150 | })); 151 | encodeComboBox.addActionListener(e -> encodeComboBoxActionPerformed(e)); 152 | add(encodeComboBox, new GridBagConstraints(1, 2, 1, 1, 0.0, 0.0, 153 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 154 | new Insets(0, 0, 5, 5), 0, 0)); 155 | 156 | //---- decodeComboBox ---- 157 | decodeComboBox.setModel(new DefaultComboBoxModel<>(new String[] { 158 | "Decode as" 159 | })); 160 | decodeComboBox.addActionListener(e -> decodeComboBoxActionPerformed(e)); 161 | add(decodeComboBox, new GridBagConstraints(2, 2, 1, 1, 0.0, 0.0, 162 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 163 | new Insets(0, 0, 5, 5), 0, 0)); 164 | 165 | //---- decryptComboBox ---- 166 | decryptComboBox.setModel(new DefaultComboBoxModel<>(new String[] { 167 | "Decrypt as" 168 | })); 169 | decryptComboBox.addActionListener(e -> decryptComboBoxActionPerformed(e)); 170 | add(decryptComboBox, new GridBagConstraints(3, 2, 1, 1, 0.0, 0.0, 171 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 172 | new Insets(0, 0, 5, 5), 0, 0)); 173 | 174 | //---- pluginsComboBox ---- 175 | pluginsComboBox.setModel(new DefaultComboBoxModel<>(new String[] { 176 | "Plugins as" 177 | })); 178 | pluginsComboBox.addActionListener(e -> pluginsComboBoxActionPerformed(e)); 179 | add(pluginsComboBox, new GridBagConstraints(4, 2, 1, 1, 0.0, 0.0, 180 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 181 | new Insets(0, 0, 5, 5), 0, 0)); 182 | 183 | //---- reloadPlugins ---- 184 | reloadPlugins.setText("Reload Plugins"); 185 | reloadPlugins.addActionListener(e -> reloadPluginsActionPerformed(e)); 186 | add(reloadPlugins, new GridBagConstraints(5, 2, 1, 1, 0.0, 0.0, 187 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 188 | new Insets(0, 0, 5, 5), 0, 0)); 189 | 190 | //---- resultCharacterCount ---- 191 | resultCharacterCount.setText("ResultArea - Now Result Character Count:0"); 192 | add(resultCharacterCount, new GridBagConstraints(0, 3, 7, 1, 0.0, 0.0, 193 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 194 | new Insets(0, 0, 5, 0), 0, 0)); 195 | 196 | //======== scrollPane2 ======== 197 | { 198 | 199 | //---- resultArea ---- 200 | resultArea.setLineWrap(true); 201 | scrollPane2.setViewportView(resultArea); 202 | } 203 | add(scrollPane2, new GridBagConstraints(0, 4, 7, 1, 0.0, 0.0, 204 | GridBagConstraints.CENTER, GridBagConstraints.BOTH, 205 | new Insets(0, 0, 0, 0), 0, 0)); 206 | // JFormDesigner - End of component initialization //GEN-END:initComponents 207 | //输入监听 208 | inputArea.getDocument().addDocumentListener(new DocumentListener() { 209 | @Override 210 | public void removeUpdate(DocumentEvent e) { 211 | inputCharacterChange(e); 212 | } 213 | @Override 214 | public void insertUpdate(DocumentEvent e) { 215 | inputCharacterChange(e); 216 | } 217 | @Override 218 | public void changedUpdate(DocumentEvent e) { 219 | inputCharacterChange(e); 220 | } 221 | }); 222 | //结果输出监听 223 | resultArea.getDocument().addDocumentListener(new DocumentListener() { 224 | @Override 225 | public void removeUpdate(DocumentEvent e) { 226 | resultCharacterChange(e); 227 | } 228 | @Override 229 | public void insertUpdate(DocumentEvent e) { 230 | resultCharacterChange(e); 231 | } 232 | @Override 233 | public void changedUpdate(DocumentEvent e) { 234 | resultCharacterChange(e); 235 | } 236 | }); 237 | DefaultComboBoxModel encodeModel = new DefaultComboBoxModel(new String[]{ 238 | "Encode as", 239 | CodeMode.ENCODE_MORSE, 240 | CodeMode.ENCODE_BACON, 241 | CodeMode.ENCODE_BASE64, 242 | CodeMode.ENCODE_BASE32, 243 | CodeMode.ENCODE_URL, 244 | CodeMode.ENCODE_UNICODE, 245 | CodeMode.ENCODE_HTML, 246 | CodeMode.ENCODE_VIGENERE, 247 | }); 248 | DefaultComboBoxModel decodeModel = new DefaultComboBoxModel(new String[]{ 249 | "Decode as", 250 | CodeMode.DECODE_MORSE, 251 | CodeMode.DECODE_BACON, 252 | CodeMode.DECODE_BASE64, 253 | CodeMode.DECODE_BASE32, 254 | CodeMode.DECODE_URL, 255 | CodeMode.DECODE_UNICODE, 256 | CodeMode.DECODE_HTML, 257 | CodeMode.DECODE_VIGENERE, 258 | }); 259 | DefaultComboBoxModel decryptModel = new DefaultComboBoxModel(new String[]{ 260 | "Decrypt as", 261 | CodeMode.CRYPTO_FENCE, 262 | CodeMode.CRYPTO_CAESAR, 263 | CodeMode.CRYPTO_PIG, 264 | CodeMode.CRYPTO_ROT13, 265 | CodeMode.CRYPTO_HEX_2_STRING, 266 | CodeMode.CRYPTO_STRING_2_HEX, 267 | CodeMode.CRYPTO_UNICODE_2_ASCII, 268 | CodeMode.CRYPTO_ASCII_2_UNICODE, 269 | CodeMode.CRYPTO_REVERSE 270 | }); 271 | encodeComboBox.setModel(encodeModel); 272 | decodeComboBox.setModel(decodeModel); 273 | decryptComboBox.setModel(decryptModel); 274 | loadPlugin(); 275 | } 276 | 277 | // JFormDesigner - Variables declaration - DO NOT MODIFY //GEN-BEGIN:variables 278 | private JLabel inputCharacterCount; 279 | private JScrollPane scrollPane1; 280 | private JTextArea inputArea; 281 | private JComboBox encodeComboBox; 282 | private JComboBox decodeComboBox; 283 | private JComboBox decryptComboBox; 284 | private JComboBox pluginsComboBox; 285 | private JButton reloadPlugins; 286 | private JLabel resultCharacterCount; 287 | private JScrollPane scrollPane2; 288 | private JTextArea resultArea; 289 | // JFormDesigner - End of variables declaration //GEN-END:variables 290 | private final CoreFunc func = new CoreFunc(); 291 | private final PluginsJson json = new PluginsJson(); 292 | private ArrayList> plugins = json.parseJson(); 293 | private String input; 294 | } 295 | -------------------------------------------------------------------------------- /src/burp/fuction/CoreFunc.kt: -------------------------------------------------------------------------------- 1 | package org.ctfcracktools.fuction 2 | 3 | import ctfcracktools.fuction.CodeMode 4 | import org.apache.commons.codec.binary.Base32 5 | import org.apache.commons.codec.binary.Base64.* 6 | import org.apache.commons.text.StringEscapeUtils 7 | import java.net.URLDecoder 8 | import java.net.URLEncoder 9 | import java.util.* 10 | import java.util.regex.Matcher 11 | import java.util.regex.Pattern 12 | import javax.swing.JOptionPane 13 | 14 | /** 15 | * @author 林晨0chencc 16 | * @since 2017/12/2 17 | * @version 1.0.2 18 | */ 19 | class CoreFunc{ 20 | /** 21 | * 主函数 22 | * @param input 需要加密/解密的字符串传入 23 | * @param type 加密类型 24 | * @return String 编码后的结果 25 | */ 26 | fun callFunc(input:String,type:String): String? { 27 | val funcMap = mutableMapOf( 28 | CodeMode.CRYPTO_FENCE to ::fence, 29 | CodeMode.CRYPTO_CAESAR to ::caesar, 30 | CodeMode.CRYPTO_PIG to ::pigCode, 31 | CodeMode.CRYPTO_ROT13 to ::rot13, 32 | CodeMode.CRYPTO_HEX_2_STRING to ::hextoString, 33 | CodeMode.CRYPTO_STRING_2_HEX to ::stringtoHex, 34 | CodeMode.CRYPTO_UNICODE_2_ASCII to ::unicodeToAscii, 35 | CodeMode.CRYPTO_ASCII_2_UNICODE to ::asciiToUnicode, 36 | CodeMode.CRYPTO_REVERSE to ::reverse, 37 | 38 | CodeMode.DECODE_MORSE to ::morseDecode, 39 | CodeMode.DECODE_BACON to ::baconCodeDecode, 40 | CodeMode.DECODE_BASE64 to ::base64de, 41 | CodeMode.DECODE_BASE32 to ::base32de, 42 | CodeMode.DECODE_URL to ::urlDecoder, 43 | CodeMode.DECODE_UNICODE to ::unicodeDecode, 44 | CodeMode.DECODE_HTML to ::htmlDecode, 45 | CodeMode.DECODE_VIGENERE to ::vigenereDeCode, 46 | 47 | CodeMode.ENCODE_MORSE to ::morseEncode, 48 | CodeMode.ENCODE_BACON to ::baconCodeEncode, 49 | CodeMode.ENCODE_BASE64 to ::base64en, 50 | CodeMode.ENCODE_BASE32 to ::base32en, 51 | CodeMode.ENCODE_URL to ::urlEncoder, 52 | CodeMode.ENCODE_UNICODE to ::unicodeEncode, 53 | CodeMode.ENCODE_HTML to ::htmlEncode, 54 | CodeMode.ENCODE_VIGENERE to ::vigenereEnCode,) 55 | 56 | return funcMap[type]?.let { it(input) } 57 | } 58 | 59 | /** 60 | * 栅栏密码 61 | * @param input 待加密解密的字符串 62 | * @return String 63 | */ 64 | private fun fence(input: String):String { 65 | val str:Array = arrayOfNulls(1024) 66 | val x = IntArray(1024) 67 | val result = StringBuffer() 68 | var a = 0 69 | var nums = 0 70 | if (input.length!=1&&input.length!=2) { 71 | (2 until input.length).forEach { i -> 72 | if (input.length % i == 0) { 73 | x[a] = i 74 | a++ 75 | } 76 | } 77 | } 78 | if(a!=0) { 79 | (0 until a).forEach { i -> 80 | result.append("${i + 1}:") 81 | (0 until input.length / x[i]).forEach { j -> 82 | str[nums] = input.substring(0 + (x[i] * j), x[i] + (x[i] * j)) 83 | nums++ 84 | } 85 | (0 until str[0]!!.length).forEach { ji -> 86 | (0 until nums).forEach { s -> result.append(str[s]!!.substring(ji,ji+1)) } 87 | } 88 | nums =0 89 | result.append("\n") 90 | } 91 | }else{ 92 | val newstrlenth:Int = input.replace(" ","").length 93 | if (newstrlenth !=1 && newstrlenth !=2){ 94 | (2..newstrlenth-1).forEach { i -> 95 | if (newstrlenth%i==0){ 96 | x[a]=i 97 | a++ 98 | } 99 | } 100 | } 101 | if (a != 0) { 102 | (0 until a).forEach { it -> result.append(" " + x[it]) } 103 | (0 until a).forEach { i -> 104 | result.append("${i+1}:") 105 | (0 until newstrlenth / x[i]).forEach { j -> 106 | str[nums] = input.substring(0 + x[i] * j, x[i] + x[i] * j) 107 | nums++ 108 | } 109 | (0 until str[0]!!.length).forEach { j -> 110 | (0 until nums).forEach { result.append(str[it]!!.substring(j, j + 1)) } 111 | } 112 | nums = 0 113 | result.append('\n') 114 | } 115 | } 116 | } 117 | return result.toString() 118 | } 119 | 120 | /** 121 | * 凯撒密码/Caesar Code 122 | * @param input 待加密解密的字符串 123 | * @return String 124 | */ 125 | private fun caesar(input:String):String{ 126 | val word:CharArray=input.toCharArray() 127 | val result = StringBuffer() 128 | (0 until 26).forEach { 129 | (word.indices).forEach { j -> 130 | if (word[j].isUpperCase()){ 131 | if(word[j]=='Z') word[j]='A' else word[j] = (word[j].toInt() + 1).toChar() 132 | }else if(word[j].isLowerCase()){ 133 | if(word[j]=='z') word[j]='a' else word[j]=(word[j].toInt()+1).toChar() 134 | } 135 | } 136 | result.append(word+'\n') 137 | } 138 | return result.toString() 139 | } 140 | 141 | /** 142 | * 维吉利亚密码 143 | * @param input 待加解密的字符串 144 | * @param mode VIGENERE_MODE_DECODE为解密 VIGENERE_MODE_DECODE为加密 145 | * @return String 146 | */ 147 | private fun vigenereCode(input:String,mode:String):String{ 148 | val pass = input.toCharArray() 149 | val key = JOptionPane.showInputDialog("Please input key").toCharArray() 150 | var i = 0 151 | var j:Int 152 | var q = 0 153 | var k:Int 154 | var m:Int 155 | when(mode){ 156 | CodeMode.DECODE_VIGENERE -> return StringBuilder() 157 | .let{ 158 | result -> 159 | while (i { 162 | j = q%key.size 163 | k = UpperCase.indexOf(key[j].toUpperCase()) 164 | m = UpperCase.indexOf(pass[i]) 165 | result.append(UpperCase[(m+k)%26]) 166 | q++ 167 | } 168 | pass[i].isLowerCase() -> { 169 | j = q%key.size 170 | k = LowerCase.indexOf(key[j].toLowerCase()) 171 | m = LowerCase.indexOf(pass[i]) 172 | result.append(LowerCase[(m+k)%26]) 173 | q++ 174 | } 175 | else -> result.append(pass[i]) 176 | } 177 | i++ 178 | } 179 | result 180 | } 181 | .toString() 182 | CodeMode.ENCODE_VIGENERE -> return StringBuilder() 183 | .let{ 184 | result -> 185 | while (i { 188 | j = q%key.size 189 | k = UpperCase.indexOf(key[j].toUpperCase()) 190 | m = UpperCase.indexOf(pass[i]) 191 | if(m { 197 | j = q%key.size 198 | k = LowerCase.indexOf(key[j].toLowerCase()) 199 | m = LowerCase.indexOf(pass[i]) 200 | if(m result.append(pass[i]) 206 | } 207 | i++ 208 | } 209 | result 210 | } 211 | .toString() 212 | else -> return "None" 213 | } 214 | } 215 | 216 | /** 217 | * 维吉利亚密码加密 依赖vigenereCode 218 | * @param input 待加密的字符串 219 | * @return String 220 | */ 221 | 222 | private fun vigenereEnCode(input:String): String = vigenereCode(input, CodeMode.ENCODE_VIGENERE) 223 | 224 | /** 225 | * 维吉利亚解密 依赖vigenereCode 226 | * @param input 待解密的字符串 227 | * @return String 228 | */ 229 | private fun vigenereDeCode(input:String):String = vigenereCode(input, CodeMode.DECODE_VIGENERE) 230 | 231 | /** 232 | * 猪圈密码 233 | * @param input 待解密的字符串 234 | * @return String 235 | */ 236 | private fun pigCode(input:String):String{ 237 | val result = StringBuffer() 238 | val keymap= mapOf('A' to 'J','B' to 'K','C' to 'L','D' to 'M', 239 | 'E' to 'N','F' to 'O','G' to 'P','H' to 'Q','I' to 'R','J' to 'A','K' to 'B','L' to 'C', 240 | 'M' to 'D','N' to 'E','O' to 'F','P' to 'G','Q' to 'H','R' to 'I','S' to 'W','T' to 'X', 241 | 'U' to 'Y','V' to 'Z','W' to 'S','X' to 'T','Y' to 'U','Z' to 'V') 242 | val word = input.toCharArray() 243 | for (i in word.indices){ 244 | if (word[i].isUpperCase()){ 245 | result.append(keymap.get(word[i])!!) 246 | }else if(word[i].isLowerCase()){ 247 | result.append(keymap.get(word[i].toUpperCase())!!.toLowerCase()) 248 | }else{ 249 | result.append(word[i]) 250 | } 251 | } 252 | return result.toString() 253 | } 254 | 255 | /** 256 | * ROT13 257 | * @param input 待编码的字符串 258 | * @return String 259 | */ 260 | private fun rot13(input:String):String{ 261 | var word = input.toCharArray() 262 | val result = StringBuffer() 263 | for (i in 0 until word.size){ 264 | when { 265 | word[i] in 'a'..'m' -> word[i]=(word[i].toInt()+13).toChar() 266 | word[i] in 'A'..'M' -> word[i]=(word[i].toInt()+13).toChar() 267 | word[i] in 'n'..'z' -> word[i]=(word[i].toInt()-13).toChar() 268 | word[i] in 'N'..'Z' -> word[i]=(word[i].toInt()-13).toChar() 269 | } 270 | result.append(word[i]) 271 | } 272 | return result.toString() 273 | } 274 | 275 | /** 276 | * 培根密码加密 277 | * @param input 待加密的字符串 278 | * @return String 279 | */ 280 | private fun baconCodeEncode(input:String):String{ 281 | val keymap = mapOf("A" to "aaaaa","B" to "aaaab","C" to "aaaba", 282 | "D" to "aaabb","E" to "aabaa","F" to "aabab","G" to "aabba","H" to "aabbb","I" to "abaaa", 283 | "J" to "abaab","K" to "ababa","L" to "ababb","M" to "abbaa","N" to "abbab","O" to "abbba", 284 | "P" to "abbbb","Q" to "baaaa","R" to "baaab","S" to "baaba","T" to "baabb","U" to "babaa", 285 | "V" to "babab","W" to "babba","X" to "babbb","Y" to "bbaaa","Z" to "bbaab","a" to "AAAAA", 286 | "b" to "AAAAB","c" to "AAABA","d" to "AAABB","e" to "AABAA","f" to "AABAB","g" to "AABBA", 287 | "h" to "AABBB","i" to "ABAAA","j" to "ABAAB","k" to "ABABA","l" to "ABABB","m" to "ABBAA", 288 | "n" to "ABBAB","o" to "ABBBA","p" to "ABBBB","q" to "BAAAA", 289 | "r" to "BAAAB","s" to "BAABA","t" to "BAABB","u" to "BABAA","v" to "BABAB","w" to "BABBA", 290 | "x" to "BABBB","y" to "BBAAA","z" to "BBAAB") 291 | return StringBuilder() 292 | .let{ 293 | result -> 294 | if(is26word(input)) { 295 | splitNum(input,1).forEach {result.append(keymap[it])} 296 | }else{ 297 | result.append("有字符不属于26字母其中") 298 | } 299 | result 300 | } 301 | .toString() 302 | } 303 | 304 | /** 305 | * 培根密码解密 306 | * @param input 待加密的字符串 307 | * @return String 308 | */ 309 | private fun baconCodeDecode(input: String):String{ 310 | val keymap = mapOf("aaaaa" to 'A',"aaaab" to 'B',"aaaba" to 'C', 311 | "aaabb" to 'D',"aabaa" to 'E',"aabab" to 'F',"aabba" to 'G',"aabbb" to 'H',"abaaa" to 'I', 312 | "abaab" to 'J',"ababa" to 'K',"ababb" to 'L',"abbaa" to 'M',"abbab" to 'N',"abbba" to 'O', 313 | "abbbb" to 'P',"baaaa" to 'Q',"baaab" to 'R',"baaba" to 'S',"baabb" to 'T',"babaa" to 'U', 314 | "babab" to 'V',"babba" to 'W',"babbb" to 'X',"bbaaa" to 'Y',"bbaab" to 'Z',//UpperCase大写字符 315 | "AAAAA" to 'a',"AAAAB" to 'b',"AAABA" to 'c',"AAABB" to 'd',"AABAA" to 'e',"AABAB" to 'f', 316 | "AABBA" to 'g',"AABBB" to 'h',"ABAAA" to 'i',"ABAAB" to 'j',"ABABA" to 'k', 317 | "ABABB" to 'l',"ABBAA" to 'm',"ABBAB" to 'n',"ABBBA" to 'o', "ABBBB" to 'p',"BAAAA" to 'q', 318 | "BAAAB" to 'r',"BAABA" to 's',"BAABB" to 't',"BABAA" to 'u',"BABAB" to 'v',"BABBA" to 'w', 319 | "BABBB" to 'x',"BBAAA" to 'y',"BBAAB" to 'z' 320 | ) 321 | return StringBuilder() 322 | .let{ 323 | result -> 324 | if(isBacon(input)){ 325 | val inputnew = input.replace(" ","") 326 | splitNum(inputnew,5,"[ab]{5}").forEach { result.append(keymap[it]) } 327 | }else{ 328 | result.append("并非是培根密码") 329 | } 330 | result 331 | } 332 | .toString() 333 | } 334 | 335 | private fun base64de(input: String):String = String(decodeBase64(input)) 336 | private fun base64en(input: String):String = encodeBase64String(input.toByteArray()) 337 | private fun base32de(input:String):String = String(Base32().decode(input)) 338 | private fun base32en(input:String):String = Base32().encodeAsString(input.toByteArray()) 339 | 340 | /** 341 | * 16进制转字符串 342 | * @param input 待编码的字符串 343 | * @return String 344 | */ 345 | private fun hextoString(input:String):String{ 346 | return StringBuilder() 347 | .let{ 348 | result -> 349 | (0 until input.length-1 step 2) 350 | .map{ input.substring(it, it+2) } 351 | .map { Integer.parseInt(it,16) } 352 | .forEach { result.append(it.toChar()) } 353 | result 354 | } 355 | .toString() 356 | } 357 | 358 | /** 359 | * 字符串转16进制 360 | * @param input 待编码的字符串 361 | * @return String 362 | */ 363 | private fun stringtoHex(input:String):String{ 364 | return StringBuilder() 365 | .let{ 366 | result -> 367 | input.toCharArray().forEach {result.append(Integer.toHexString(it.toInt())) } 368 | result 369 | } 370 | .toString() 371 | } 372 | 373 | /** 374 | * 摩斯电码编码 375 | * @param input 待编码的字符串 376 | * @return String 377 | */ 378 | private fun morseEncode(input: String):String { 379 | return StringBuilder() 380 | .let{ 381 | result -> 382 | input.toLowerCase().toCharArray().forEach { 383 | when { 384 | isChar(it) -> result.append(morseCharacters[(it - 'a')]+" ") 385 | isDigit(it) -> result.append(morseDigits[(it - '0')]+" ") 386 | } 387 | } 388 | result 389 | } 390 | .toString() 391 | } 392 | 393 | /** 394 | * 摩斯密码解码 395 | * @param input 待解码的字符串 396 | * @return String 397 | */ 398 | private fun morseDecode(input:String):String{ 399 | initMorseTable() 400 | val morse=format(input) 401 | val st=StringTokenizer(morse) 402 | val result=StringBuilder(morse.length / 2) 403 | while (st.hasMoreTokens()) { 404 | result.append(htMorse[st.nextToken()]) 405 | } 406 | return result.toString() 407 | } 408 | 409 | private fun urlEncoder(input: String):String = URLEncoder.encode(input,"utf-8").replace("+","%20")//Url编码加密 410 | private fun urlDecoder(input: String):String = URLDecoder.decode(input,"utf-8")//Url编码解密 411 | private fun unicodeEncode(input: String):String{ 412 | return StringBuilder() 413 | .let { 414 | result -> 415 | input.toCharArray().forEach {result.append("\\u"+Integer.toHexString(it.toInt())) } 416 | result 417 | } 418 | .toString() 419 | } 420 | private fun unicodeDecode(input: String):String{ 421 | return StringBuilder() 422 | .let{ 423 | result -> 424 | val hex=input.split("\\u") 425 | (1 until hex.size) 426 | .map { Integer.parseInt(hex[it], 16) } 427 | .forEach { result.append(it.toChar()) } 428 | result 429 | } 430 | .toString() 431 | } 432 | 433 | /** 434 | * Unicode编码转Ascii编码 435 | * @param input 待编码的字符串 436 | * @return String 437 | */ 438 | private fun unicodeToAscii(input:String):String{ 439 | return StringBuilder() 440 | .let{ 441 | result -> 442 | val pout = Pattern.compile("\\&\\#(\\d+)").matcher(input) 443 | while (pout.find()){ result.append(Integer.valueOf(pout.group(1)).toInt().toChar()) } 444 | result 445 | } 446 | .toString() 447 | } 448 | 449 | /** 450 | * Ascii编码转Unicode编码 451 | * @param input 待编码的字符串 452 | * @return String 453 | */ 454 | private fun asciiToUnicode(input: String):String{ 455 | return StringBuilder() 456 | .let { 457 | result -> 458 | input.toCharArray().forEach { result.append("&#"+it.toInt()+";")} 459 | result 460 | } 461 | .toString() 462 | } 463 | 464 | /** 465 | * 字符翻转,顾名思义 466 | * @param input 待翻转的字符串 467 | * @return String 468 | */ 469 | private fun reverse(input:String):String{ 470 | val result = StringBuilder() 471 | val tmp = input.toCharArray() 472 | var a=tmp.size-1 473 | while (a > -1) { 474 | result.append(tmp[a]) 475 | a-=1 476 | } 477 | return result.toString() 478 | } 479 | /* fun HillCodeEncode(input:String,key:String):String{ 480 | val keymatrix:CharArray = key.split(" ") as CharArray 481 | var tmp[]:Array 482 | when{ 483 | keymatrix.size/4 == 0 -> 484 | 0 until keymatrix.size%4.forEach{ 485 | 486 | } 487 | 488 | } 489 | return StringBuffer() 490 | .let { 491 | result-> 492 | 493 | } 494 | .toString() 495 | }*/ 496 | private fun htmlEncode(input:String): String = StringEscapeUtils.escapeHtml4(input) 497 | private fun htmlDecode(input:String):String = StringEscapeUtils.unescapeHtml4(input) 498 | /* 内置方法/内置常量 */ 499 | private val UpperCase:String ="ABCDEFGHIJKLMNOPQRSTUVWXYZ" 500 | private val LowerCase:String = "abcdefghijklmnopqrstuvwxyz" 501 | // private val SplitString = {//多次切割字符串 502 | // input:String -> 503 | // val tmp = input.split(",") 504 | // val result = StringBuilder() 505 | // tmp.forEach{ 506 | // val tmp_1 = it.split(" to ") 507 | // result.append(tmp_1[1]+" to "+tmp_1[0]+",") 508 | // } 509 | // result.toString() 510 | // } 511 | private fun splitNum(input:String,num:Int):Array{ 512 | val str:Array = arrayOfNulls(input.length/num) 513 | (1..input.length/num).forEach { i->str.set(i-1,input.substring(i*num-num,i*num)) } 514 | return str 515 | } 516 | private fun splitNum(input:String,num:Int,pattern:String):Array{ 517 | val r:Pattern = Pattern.compile(pattern) 518 | val m: Matcher = r.matcher(input) 519 | var input_m = "" 520 | var a = true 521 | while (a){ 522 | if(!m.find()) a=false else input_m += m.group() 523 | } 524 | return splitNum(input_m,num) 525 | } 526 | val isBacon = { 527 | input:String -> 528 | var tmp:Boolean = false 529 | input.toCharArray().forEach { 530 | tmp = (it=='A'||it=='B')||(it == 'a'||it=='b') 531 | } 532 | tmp 533 | } 534 | val is26word = { 535 | input:String -> 536 | var tmp = false 537 | input.toCharArray().forEach { 538 | tmp = isChar(it) 539 | } 540 | tmp 541 | } 542 | var htMorse: Hashtable = Hashtable() 543 | private fun initMorseTable(){ 544 | (0..25).forEach { i -> htMorse.put(morseCharacters[i], Character.valueOf((65+i).toChar())) } 545 | (0..9).forEach { i -> htMorse.put(morseDigits[i], Character.valueOf((48+i).toChar())) } 546 | } 547 | val isChar = {c:Char -> c.isLowerCase()||c.isUpperCase()} 548 | val isDigit = {c:Char -> (c >='0')&&(c <= '9')} 549 | /* moresCode */ 550 | private val morseCharacters = arrayOf(".-", "-...", "-.-.", "-..", ".", "..-.", "--.", "....", "src", ".---", 551 | "-.-", ".-..", "--", "-.", "---", ".--.", "--.-", ".-.", "...", "-", "..-", "...-", ".--", "-..-", "-.--", 552 | "--..") 553 | private val morseDigits = arrayOf("-----", ".----", "..---", "...--", "....-", ".....", "-....", "--...", 554 | "---..", "----.") 555 | val format = { 556 | input:String-> 557 | val word = input.toCharArray() 558 | val result = StringBuilder() 559 | for(i in word.indices){ 560 | when{ 561 | word[i] == '\n' -> word[i]=' ' 562 | word[i] == '.' -> { 563 | result.append(word[i]) 564 | } 565 | word[i] == '-' -> { 566 | result.append(word[i]) 567 | } 568 | word[i] == ' ' -> { 569 | result.append(word[i]) 570 | } 571 | } 572 | } 573 | result.toString() 574 | } 575 | } 576 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | GNU GENERAL PUBLIC LICENSE 2 | Version 3, 29 June 2007 3 | 4 | Copyright (C) 2007 Free Software Foundation, Inc. 5 | Everyone is permitted to copy and distribute verbatim copies 6 | of this license document, but changing it is not allowed. 7 | 8 | Preamble 9 | 10 | The GNU General Public License is a free, copyleft license for 11 | software and other kinds of works. 12 | 13 | The licenses for most software and other practical works are designed 14 | to take away your freedom to share and change the works. By contrast, 15 | the GNU General Public License is intended to guarantee your freedom to 16 | share and change all versions of a program--to make sure it remains free 17 | software for all its users. We, the Free Software Foundation, use the 18 | GNU General Public License for most of our software; it applies also to 19 | any other work released this way by its authors. You can apply it to 20 | your programs, too. 21 | 22 | When we speak of free software, we are referring to freedom, not 23 | price. Our General Public Licenses are designed to make sure that you 24 | have the freedom to distribute copies of free software (and charge for 25 | them if you wish), that you receive source code or can get it if you 26 | want it, that you can change the software or use pieces of it in new 27 | free programs, and that you know you can do these things. 28 | 29 | To protect your rights, we need to prevent others from denying you 30 | these rights or asking you to surrender the rights. Therefore, you have 31 | certain responsibilities if you distribute copies of the software, or if 32 | you modify it: responsibilities to respect the freedom of others. 33 | 34 | For example, if you distribute copies of such a program, whether 35 | gratis or for a fee, you must pass on to the recipients the same 36 | freedoms that you received. You must make sure that they, too, receive 37 | or can get the source code. And you must show them these terms so they 38 | know their rights. 39 | 40 | Developers that use the GNU GPL protect your rights with two steps: 41 | (1) assert copyright on the software, and (2) offer you this License 42 | giving you legal permission to copy, distribute and/or modify it. 43 | 44 | For the developers' and authors' protection, the GPL clearly explains 45 | that there is no warranty for this free software. For both users' and 46 | authors' sake, the GPL requires that modified versions be marked as 47 | changed, so that their problems will not be attributed erroneously to 48 | authors of previous versions. 49 | 50 | Some devices are designed to deny users access to install or run 51 | modified versions of the software inside them, although the manufacturer 52 | can do so. This is fundamentally incompatible with the aim of 53 | protecting users' freedom to change the software. The systematic 54 | pattern of such abuse occurs in the area of products for individuals to 55 | use, which is precisely where it is most unacceptable. Therefore, we 56 | have designed this version of the GPL to prohibit the practice for those 57 | products. If such problems arise substantially in other domains, we 58 | stand ready to extend this provision to those domains in future versions 59 | of the GPL, as needed to protect the freedom of users. 60 | 61 | Finally, every program is threatened constantly by software patents. 62 | States should not allow patents to restrict development and use of 63 | software on general-purpose computers, but in those that do, we wish to 64 | avoid the special danger that patents applied to a free program could 65 | make it effectively proprietary. To prevent this, the GPL assures that 66 | patents cannot be used to render the program non-free. 67 | 68 | The precise terms and conditions for copying, distribution and 69 | modification follow. 70 | 71 | TERMS AND CONDITIONS 72 | 73 | 0. Definitions. 74 | 75 | "This License" refers to version 3 of the GNU General Public License. 76 | 77 | "Copyright" also means copyright-like laws that apply to other kinds of 78 | works, such as semiconductor masks. 79 | 80 | "The Program" refers to any copyrightable work licensed under this 81 | License. Each licensee is addressed as "you". "Licensees" and 82 | "recipients" may be individuals or organizations. 83 | 84 | To "modify" a work means to copy from or adapt all or part of the work 85 | in a fashion requiring copyright permission, other than the making of an 86 | exact copy. The resulting work is called a "modified version" of the 87 | earlier work or a work "based on" the earlier work. 88 | 89 | A "covered work" means either the unmodified Program or a work based 90 | on the Program. 91 | 92 | To "propagate" a work means to do anything with it that, without 93 | permission, would make you directly or secondarily liable for 94 | infringement under applicable copyright law, except executing it on a 95 | computer or modifying a private copy. Propagation includes copying, 96 | distribution (with or without modification), making available to the 97 | public, and in some countries other activities as well. 98 | 99 | To "convey" a work means any kind of propagation that enables other 100 | parties to make or receive copies. Mere interaction with a user through 101 | a computer network, with no transfer of a copy, is not conveying. 102 | 103 | An interactive user interface displays "Appropriate Legal Notices" 104 | to the extent that it includes a convenient and prominently visible 105 | feature that (1) displays an appropriate copyright notice, and (2) 106 | tells the user that there is no warranty for the work (except to the 107 | extent that warranties are provided), that licensees may convey the 108 | work under this License, and how to view a copy of this License. If 109 | the interface presents a list of user commands or options, such as a 110 | menu, a prominent item in the list meets this criterion. 111 | 112 | 1. Source Code. 113 | 114 | The "source code" for a work means the preferred form of the work 115 | for making modifications to it. "Object code" means any non-source 116 | form of a work. 117 | 118 | A "Standard Interface" means an interface that either is an official 119 | standard defined by a recognized standards body, or, in the case of 120 | interfaces specified for a particular programming language, one that 121 | is widely used among developers working in that language. 122 | 123 | The "System Libraries" of an executable work include anything, other 124 | than the work as a whole, that (a) is included in the normal form of 125 | packaging a Major Component, but which is not part of that Major 126 | Component, and (b) serves only to enable use of the work with that 127 | Major Component, or to implement a Standard Interface for which an 128 | implementation is available to the public in source code form. A 129 | "Major Component", in this context, means a major essential component 130 | (kernel, window system, and so on) of the specific operating system 131 | (if any) on which the executable work runs, or a compiler used to 132 | produce the work, or an object code interpreter used to run it. 133 | 134 | The "Corresponding Source" for a work in object code form means all 135 | the source code needed to generate, install, and (for an executable 136 | work) run the object code and to modify the work, including scripts to 137 | control those activities. However, it does not include the work's 138 | System Libraries, or general-purpose tools or generally available free 139 | programs which are used unmodified in performing those activities but 140 | which are not part of the work. For example, Corresponding Source 141 | includes interface definition files associated with source files for 142 | the work, and the source code for shared libraries and dynamically 143 | linked subprograms that the work is specifically designed to require, 144 | such as by intimate data communication or control flow between those 145 | subprograms and other parts of the work. 146 | 147 | The Corresponding Source need not include anything that users 148 | can regenerate automatically from other parts of the Corresponding 149 | Source. 150 | 151 | The Corresponding Source for a work in source code form is that 152 | same work. 153 | 154 | 2. Basic Permissions. 155 | 156 | All rights granted under this License are granted for the term of 157 | copyright on the Program, and are irrevocable provided the stated 158 | conditions are met. This License explicitly affirms your unlimited 159 | permission to run the unmodified Program. The output from running a 160 | covered work is covered by this License only if the output, given its 161 | content, constitutes a covered work. This License acknowledges your 162 | rights of fair use or other equivalent, as provided by copyright law. 163 | 164 | You may make, run and propagate covered works that you do not 165 | convey, without conditions so long as your license otherwise remains 166 | in force. You may convey covered works to others for the sole purpose 167 | of having them make modifications exclusively for you, or provide you 168 | with facilities for running those works, provided that you comply with 169 | the terms of this License in conveying all material for which you do 170 | not control copyright. Those thus making or running the covered works 171 | for you must do so exclusively on your behalf, under your direction 172 | and control, on terms that prohibit them from making any copies of 173 | your copyrighted material outside their relationship with you. 174 | 175 | Conveying under any other circumstances is permitted solely under 176 | the conditions stated below. Sublicensing is not allowed; section 10 177 | makes it unnecessary. 178 | 179 | 3. Protecting Users' Legal Rights From Anti-Circumvention Law. 180 | 181 | No covered work shall be deemed part of an effective technological 182 | measure under any applicable law fulfilling obligations under article 183 | 11 of the WIPO copyright treaty adopted on 20 December 1996, or 184 | similar laws prohibiting or restricting circumvention of such 185 | measures. 186 | 187 | When you convey a covered work, you waive any legal power to forbid 188 | circumvention of technological measures to the extent such circumvention 189 | is effected by exercising rights under this License with respect to 190 | the covered work, and you disclaim any intention to limit operation or 191 | modification of the work as a means of enforcing, against the work's 192 | users, your or third parties' legal rights to forbid circumvention of 193 | technological measures. 194 | 195 | 4. Conveying Verbatim Copies. 196 | 197 | You may convey verbatim copies of the Program's source code as you 198 | receive it, in any medium, provided that you conspicuously and 199 | appropriately publish on each copy an appropriate copyright notice; 200 | keep intact all notices stating that this License and any 201 | non-permissive terms added in accord with section 7 apply to the code; 202 | keep intact all notices of the absence of any warranty; and give all 203 | recipients a copy of this License along with the Program. 204 | 205 | You may charge any price or no price for each copy that you convey, 206 | and you may offer support or warranty protection for a fee. 207 | 208 | 5. Conveying Modified Source Versions. 209 | 210 | You may convey a work based on the Program, or the modifications to 211 | produce it from the Program, in the form of source code under the 212 | terms of section 4, provided that you also meet all of these conditions: 213 | 214 | a) The work must carry prominent notices stating that you modified 215 | it, and giving a relevant date. 216 | 217 | b) The work must carry prominent notices stating that it is 218 | released under this License and any conditions added under section 219 | 7. This requirement modifies the requirement in section 4 to 220 | "keep intact all notices". 221 | 222 | c) You must license the entire work, as a whole, under this 223 | License to anyone who comes into possession of a copy. This 224 | License will therefore apply, along with any applicable section 7 225 | additional terms, to the whole of the work, and all its parts, 226 | regardless of how they are packaged. This License gives no 227 | permission to license the work in any other way, but it does not 228 | invalidate such permission if you have separately received it. 229 | 230 | d) If the work has interactive user interfaces, each must display 231 | Appropriate Legal Notices; however, if the Program has interactive 232 | interfaces that do not display Appropriate Legal Notices, your 233 | work need not make them do so. 234 | 235 | A compilation of a covered work with other separate and independent 236 | works, which are not by their nature extensions of the covered work, 237 | and which are not combined with it such as to form a larger program, 238 | in or on a volume of a storage or distribution medium, is called an 239 | "aggregate" if the compilation and its resulting copyright are not 240 | used to limit the access or legal rights of the compilation's users 241 | beyond what the individual works permit. Inclusion of a covered work 242 | in an aggregate does not cause this License to apply to the other 243 | parts of the aggregate. 244 | 245 | 6. Conveying Non-Source Forms. 246 | 247 | You may convey a covered work in object code form under the terms 248 | of sections 4 and 5, provided that you also convey the 249 | machine-readable Corresponding Source under the terms of this License, 250 | in one of these ways: 251 | 252 | a) Convey the object code in, or embodied in, a physical product 253 | (including a physical distribution medium), accompanied by the 254 | Corresponding Source fixed on a durable physical medium 255 | customarily used for software interchange. 256 | 257 | b) Convey the object code in, or embodied in, a physical product 258 | (including a physical distribution medium), accompanied by a 259 | written offer, valid for at least three years and valid for as 260 | long as you offer spare parts or customer support for that product 261 | model, to give anyone who possesses the object code either (1) a 262 | copy of the Corresponding Source for all the software in the 263 | product that is covered by this License, on a durable physical 264 | medium customarily used for software interchange, for a price no 265 | more than your reasonable cost of physically performing this 266 | conveying of source, or (2) access to copy the 267 | Corresponding Source from a network server at no charge. 268 | 269 | c) Convey individual copies of the object code with a copy of the 270 | written offer to provide the Corresponding Source. This 271 | alternative is allowed only occasionally and noncommercially, and 272 | only if you received the object code with such an offer, in accord 273 | with subsection 6b. 274 | 275 | d) Convey the object code by offering access from a designated 276 | place (gratis or for a charge), and offer equivalent access to the 277 | Corresponding Source in the same way through the same place at no 278 | further charge. You need not require recipients to copy the 279 | Corresponding Source along with the object code. If the place to 280 | copy the object code is a network server, the Corresponding Source 281 | may be on a different server (operated by you or a third party) 282 | that supports equivalent copying facilities, provided you maintain 283 | clear directions next to the object code saying where to find the 284 | Corresponding Source. Regardless of what server hosts the 285 | Corresponding Source, you remain obligated to ensure that it is 286 | available for as long as needed to satisfy these requirements. 287 | 288 | e) Convey the object code using peer-to-peer transmission, provided 289 | you inform other peers where the object code and Corresponding 290 | Source of the work are being offered to the general public at no 291 | charge under subsection 6d. 292 | 293 | A separable portion of the object code, whose source code is excluded 294 | from the Corresponding Source as a System Library, need not be 295 | included in conveying the object code work. 296 | 297 | A "User Product" is either (1) a "consumer product", which means any 298 | tangible personal property which is normally used for personal, family, 299 | or household purposes, or (2) anything designed or sold for incorporation 300 | into a dwelling. In determining whether a product is a consumer product, 301 | doubtful cases shall be resolved in favor of coverage. For a particular 302 | product received by a particular user, "normally used" refers to a 303 | typical or common use of that class of product, regardless of the status 304 | of the particular user or of the way in which the particular user 305 | actually uses, or expects or is expected to use, the product. A product 306 | is a consumer product regardless of whether the product has substantial 307 | commercial, industrial or non-consumer uses, unless such uses represent 308 | the only significant mode of use of the product. 309 | 310 | "Installation Information" for a User Product means any methods, 311 | procedures, authorization keys, or other information required to install 312 | and execute modified versions of a covered work in that User Product from 313 | a modified version of its Corresponding Source. The information must 314 | suffice to ensure that the continued functioning of the modified object 315 | code is in no case prevented or interfered with solely because 316 | modification has been made. 317 | 318 | If you convey an object code work under this section in, or with, or 319 | specifically for use in, a User Product, and the conveying occurs as 320 | part of a transaction in which the right of possession and use of the 321 | User Product is transferred to the recipient in perpetuity or for a 322 | fixed term (regardless of how the transaction is characterized), the 323 | Corresponding Source conveyed under this section must be accompanied 324 | by the Installation Information. But this requirement does not apply 325 | if neither you nor any third party retains the ability to install 326 | modified object code on the User Product (for example, the work has 327 | been installed in ROM). 328 | 329 | The requirement to provide Installation Information does not include a 330 | requirement to continue to provide support service, warranty, or updates 331 | for a work that has been modified or installed by the recipient, or for 332 | the User Product in which it has been modified or installed. Access to a 333 | network may be denied when the modification itself materially and 334 | adversely affects the operation of the network or violates the rules and 335 | protocols for communication across the network. 336 | 337 | Corresponding Source conveyed, and Installation Information provided, 338 | in accord with this section must be in a format that is publicly 339 | documented (and with an implementation available to the public in 340 | source code form), and must require no special password or key for 341 | unpacking, reading or copying. 342 | 343 | 7. Additional Terms. 344 | 345 | "Additional permissions" are terms that supplement the terms of this 346 | License by making exceptions from one or more of its conditions. 347 | Additional permissions that are applicable to the entire Program shall 348 | be treated as though they were included in this License, to the extent 349 | that they are valid under applicable law. If additional permissions 350 | apply only to part of the Program, that part may be used separately 351 | under those permissions, but the entire Program remains governed by 352 | this License without regard to the additional permissions. 353 | 354 | When you convey a copy of a covered work, you may at your option 355 | remove any additional permissions from that copy, or from any part of 356 | it. (Additional permissions may be written to require their own 357 | removal in certain cases when you modify the work.) You may place 358 | additional permissions on material, added by you to a covered work, 359 | for which you have or can give appropriate copyright permission. 360 | 361 | Notwithstanding any other provision of this License, for material you 362 | add to a covered work, you may (if authorized by the copyright holders of 363 | that material) supplement the terms of this License with terms: 364 | 365 | a) Disclaiming warranty or limiting liability differently from the 366 | terms of sections 15 and 16 of this License; or 367 | 368 | b) Requiring preservation of specified reasonable legal notices or 369 | author attributions in that material or in the Appropriate Legal 370 | Notices displayed by works containing it; or 371 | 372 | c) Prohibiting misrepresentation of the origin of that material, or 373 | requiring that modified versions of such material be marked in 374 | reasonable ways as different from the original version; or 375 | 376 | d) Limiting the use for publicity purposes of names of licensors or 377 | authors of the material; or 378 | 379 | e) Declining to grant rights under trademark law for use of some 380 | trade names, trademarks, or service marks; or 381 | 382 | f) Requiring indemnification of licensors and authors of that 383 | material by anyone who conveys the material (or modified versions of 384 | it) with contractual assumptions of liability to the recipient, for 385 | any liability that these contractual assumptions directly impose on 386 | those licensors and authors. 387 | 388 | All other non-permissive additional terms are considered "further 389 | restrictions" within the meaning of section 10. If the Program as you 390 | received it, or any part of it, contains a notice stating that it is 391 | governed by this License along with a term that is a further 392 | restriction, you may remove that term. If a license document contains 393 | a further restriction but permits relicensing or conveying under this 394 | License, you may add to a covered work material governed by the terms 395 | of that license document, provided that the further restriction does 396 | not survive such relicensing or conveying. 397 | 398 | If you add terms to a covered work in accord with this section, you 399 | must place, in the relevant source files, a statement of the 400 | additional terms that apply to those files, or a notice indicating 401 | where to find the applicable terms. 402 | 403 | Additional terms, permissive or non-permissive, may be stated in the 404 | form of a separately written license, or stated as exceptions; 405 | the above requirements apply either way. 406 | 407 | 8. Termination. 408 | 409 | You may not propagate or modify a covered work except as expressly 410 | provided under this License. Any attempt otherwise to propagate or 411 | modify it is void, and will automatically terminate your rights under 412 | this License (including any patent licenses granted under the third 413 | paragraph of section 11). 414 | 415 | However, if you cease all violation of this License, then your 416 | license from a particular copyright holder is reinstated (a) 417 | provisionally, unless and until the copyright holder explicitly and 418 | finally terminates your license, and (b) permanently, if the copyright 419 | holder fails to notify you of the violation by some reasonable means 420 | prior to 60 days after the cessation. 421 | 422 | Moreover, your license from a particular copyright holder is 423 | reinstated permanently if the copyright holder notifies you of the 424 | violation by some reasonable means, this is the first time you have 425 | received notice of violation of this License (for any work) from that 426 | copyright holder, and you cure the violation prior to 30 days after 427 | your receipt of the notice. 428 | 429 | Termination of your rights under this section does not terminate the 430 | licenses of parties who have received copies or rights from you under 431 | this License. If your rights have been terminated and not permanently 432 | reinstated, you do not qualify to receive new licenses for the same 433 | material under section 10. 434 | 435 | 9. Acceptance Not Required for Having Copies. 436 | 437 | You are not required to accept this License in order to receive or 438 | run a copy of the Program. Ancillary propagation of a covered work 439 | occurring solely as a consequence of using peer-to-peer transmission 440 | to receive a copy likewise does not require acceptance. However, 441 | nothing other than this License grants you permission to propagate or 442 | modify any covered work. These actions infringe copyright if you do 443 | not accept this License. Therefore, by modifying or propagating a 444 | covered work, you indicate your acceptance of this License to do so. 445 | 446 | 10. Automatic Licensing of Downstream Recipients. 447 | 448 | Each time you convey a covered work, the recipient automatically 449 | receives a license from the original licensors, to run, modify and 450 | propagate that work, subject to this License. You are not responsible 451 | for enforcing compliance by third parties with this License. 452 | 453 | An "entity transaction" is a transaction transferring control of an 454 | organization, or substantially all assets of one, or subdividing an 455 | organization, or merging organizations. If propagation of a covered 456 | work results from an entity transaction, each party to that 457 | transaction who receives a copy of the work also receives whatever 458 | licenses to the work the party's predecessor in interest had or could 459 | give under the previous paragraph, plus a right to possession of the 460 | Corresponding Source of the work from the predecessor in interest, if 461 | the predecessor has it or can get it with reasonable efforts. 462 | 463 | You may not impose any further restrictions on the exercise of the 464 | rights granted or affirmed under this License. For example, you may 465 | not impose a license fee, royalty, or other charge for exercise of 466 | rights granted under this License, and you may not initiate litigation 467 | (including a cross-claim or counterclaim in a lawsuit) alleging that 468 | any patent claim is infringed by making, using, selling, offering for 469 | sale, or importing the Program or any portion of it. 470 | 471 | 11. Patents. 472 | 473 | A "contributor" is a copyright holder who authorizes use under this 474 | License of the Program or a work on which the Program is based. The 475 | work thus licensed is called the contributor's "contributor version". 476 | 477 | A contributor's "essential patent claims" are all patent claims 478 | owned or controlled by the contributor, whether already acquired or 479 | hereafter acquired, that would be infringed by some manner, permitted 480 | by this License, of making, using, or selling its contributor version, 481 | but do not include claims that would be infringed only as a 482 | consequence of further modification of the contributor version. For 483 | purposes of this definition, "control" includes the right to grant 484 | patent sublicenses in a manner consistent with the requirements of 485 | this License. 486 | 487 | Each contributor grants you a non-exclusive, worldwide, royalty-free 488 | patent license under the contributor's essential patent claims, to 489 | make, use, sell, offer for sale, import and otherwise run, modify and 490 | propagate the contents of its contributor version. 491 | 492 | In the following three paragraphs, a "patent license" is any express 493 | agreement or commitment, however denominated, not to enforce a patent 494 | (such as an express permission to practice a patent or covenant not to 495 | sue for patent infringement). To "grant" such a patent license to a 496 | party means to make such an agreement or commitment not to enforce a 497 | patent against the party. 498 | 499 | If you convey a covered work, knowingly relying on a patent license, 500 | and the Corresponding Source of the work is not available for anyone 501 | to copy, free of charge and under the terms of this License, through a 502 | publicly available network server or other readily accessible means, 503 | then you must either (1) cause the Corresponding Source to be so 504 | available, or (2) arrange to deprive yourself of the benefit of the 505 | patent license for this particular work, or (3) arrange, in a manner 506 | consistent with the requirements of this License, to extend the patent 507 | license to downstream recipients. "Knowingly relying" means you have 508 | actual knowledge that, but for the patent license, your conveying the 509 | covered work in a country, or your recipient's use of the covered work 510 | in a country, would infringe one or more identifiable patents in that 511 | country that you have reason to believe are valid. 512 | 513 | If, pursuant to or in connection with a single transaction or 514 | arrangement, you convey, or propagate by procuring conveyance of, a 515 | covered work, and grant a patent license to some of the parties 516 | receiving the covered work authorizing them to use, propagate, modify 517 | or convey a specific copy of the covered work, then the patent license 518 | you grant is automatically extended to all recipients of the covered 519 | work and works based on it. 520 | 521 | A patent license is "discriminatory" if it does not include within 522 | the scope of its coverage, prohibits the exercise of, or is 523 | conditioned on the non-exercise of one or more of the rights that are 524 | specifically granted under this License. You may not convey a covered 525 | work if you are a party to an arrangement with a third party that is 526 | in the business of distributing software, under which you make payment 527 | to the third party based on the extent of your activity of conveying 528 | the work, and under which the third party grants, to any of the 529 | parties who would receive the covered work from you, a discriminatory 530 | patent license (a) in connection with copies of the covered work 531 | conveyed by you (or copies made from those copies), or (b) primarily 532 | for and in connection with specific products or compilations that 533 | contain the covered work, unless you entered into that arrangement, 534 | or that patent license was granted, prior to 28 March 2007. 535 | 536 | Nothing in this License shall be construed as excluding or limiting 537 | any implied license or other defenses to infringement that may 538 | otherwise be available to you under applicable patent law. 539 | 540 | 12. No Surrender of Others' Freedom. 541 | 542 | If conditions are imposed on you (whether by court order, agreement or 543 | otherwise) that contradict the conditions of this License, they do not 544 | excuse you from the conditions of this License. If you cannot convey a 545 | covered work so as to satisfy simultaneously your obligations under this 546 | License and any other pertinent obligations, then as a consequence you may 547 | not convey it at all. For example, if you agree to terms that obligate you 548 | to collect a royalty for further conveying from those to whom you convey 549 | the Program, the only way you could satisfy both those terms and this 550 | License would be to refrain entirely from conveying the Program. 551 | 552 | 13. Use with the GNU Affero General Public License. 553 | 554 | Notwithstanding any other provision of this License, you have 555 | permission to link or combine any covered work with a work licensed 556 | under version 3 of the GNU Affero General Public License into a single 557 | combined work, and to convey the resulting work. The terms of this 558 | License will continue to apply to the part which is the covered work, 559 | but the special requirements of the GNU Affero General Public License, 560 | section 13, concerning interaction through a network will apply to the 561 | combination as such. 562 | 563 | 14. Revised Versions of this License. 564 | 565 | The Free Software Foundation may publish revised and/or new versions of 566 | the GNU General Public License from time to time. Such new versions will 567 | be similar in spirit to the present version, but may differ in detail to 568 | address new problems or concerns. 569 | 570 | Each version is given a distinguishing version number. If the 571 | Program specifies that a certain numbered version of the GNU General 572 | Public License "or any later version" applies to it, you have the 573 | option of following the terms and conditions either of that numbered 574 | version or of any later version published by the Free Software 575 | Foundation. If the Program does not specify a version number of the 576 | GNU General Public License, you may choose any version ever published 577 | by the Free Software Foundation. 578 | 579 | If the Program specifies that a proxy can decide which future 580 | versions of the GNU General Public License can be used, that proxy's 581 | public statement of acceptance of a version permanently authorizes you 582 | to choose that version for the Program. 583 | 584 | Later license versions may give you additional or different 585 | permissions. However, no additional obligations are imposed on any 586 | author or copyright holder as a result of your choosing to follow a 587 | later version. 588 | 589 | 15. Disclaimer of Warranty. 590 | 591 | THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY 592 | APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT 593 | HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY 594 | OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, 595 | THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 596 | PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM 597 | IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF 598 | ALL NECESSARY SERVICING, REPAIR OR CORRECTION. 599 | 600 | 16. Limitation of Liability. 601 | 602 | IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING 603 | WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS 604 | THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY 605 | GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE 606 | USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF 607 | DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD 608 | PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), 609 | EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF 610 | SUCH DAMAGES. 611 | 612 | 17. Interpretation of Sections 15 and 16. 613 | 614 | If the disclaimer of warranty and limitation of liability provided 615 | above cannot be given local legal effect according to their terms, 616 | reviewing courts shall apply local law that most closely approximates 617 | an absolute waiver of all civil liability in connection with the 618 | Program, unless a warranty or assumption of liability accompanies a 619 | copy of the Program in return for a fee. 620 | 621 | END OF TERMS AND CONDITIONS 622 | 623 | How to Apply These Terms to Your New Programs 624 | 625 | If you develop a new program, and you want it to be of the greatest 626 | possible use to the public, the best way to achieve this is to make it 627 | free software which everyone can redistribute and change under these terms. 628 | 629 | To do so, attach the following notices to the program. It is safest 630 | to attach them to the start of each source file to most effectively 631 | state the exclusion of warranty; and each file should have at least 632 | the "copyright" line and a pointer to where the full notice is found. 633 | 634 | 635 | Copyright (C) 636 | 637 | This program is free software: you can redistribute it and/or modify 638 | it under the terms of the GNU General Public License as published by 639 | the Free Software Foundation, either version 3 of the License, or 640 | (at your option) any later version. 641 | 642 | This program is distributed in the hope that it will be useful, 643 | but WITHOUT ANY WARRANTY; without even the implied warranty of 644 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 645 | GNU General Public License for more details. 646 | 647 | You should have received a copy of the GNU General Public License 648 | along with this program. If not, see . 649 | 650 | Also add information on how to contact you by electronic and paper mail. 651 | 652 | If the program does terminal interaction, make it output a short 653 | notice like this when it starts in an interactive mode: 654 | 655 | Copyright (C) 656 | This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'. 657 | This is free software, and you are welcome to redistribute it 658 | under certain conditions; type `show c' for details. 659 | 660 | The hypothetical commands `show w' and `show c' should show the appropriate 661 | parts of the General Public License. Of course, your program's commands 662 | might be different; for a GUI interface, you would use an "about box". 663 | 664 | You should also get your employer (if you work as a programmer) or school, 665 | if any, to sign a "copyright disclaimer" for the program, if necessary. 666 | For more information on this, and how to apply and follow the GNU GPL, see 667 | . 668 | 669 | The GNU General Public License does not permit incorporating your program 670 | into proprietary programs. If your program is a subroutine library, you 671 | may consider it more useful to permit linking proprietary applications with 672 | the library. If this is what you want to do, use the GNU Lesser General 673 | Public License instead of this License. But first, please read 674 | . 675 | --------------------------------------------------------------------------------