Sunday, August 22, 2010

Unhooking a leaking C# object from Microsoft.Win32.SystemEvents.UserPreferenceChanged

Before I get started I'd like to clarify what the tem "leak" means for the purposes of this discussion. Any object that your application is no longer using but cannot be garbage collected is "leaking" for the purposes of this discussion. I know that technically the memory is still accessible and it is possible to release it but the fact of the matter is that your application is not using this memory and it will not ever be released. Given enough time this will eventually lead to an out of memory exception.

For anyone that has used a memory profiler it's possible that you've come across leaks related to the System.Windows.Form.ToolStripTextBox control. If you haven't, here's a link to a blog post that can shed some light on this issue. It's a very good explanation of the problem but in summary, the ToolStripTextBox control is hooking the Microsoft.Win32.SystemEvents.UserPreferenceChanged repeatedly and unhooking only once. This is causing leaks because the UserPreferenceChanged event is static and does not go out of scope for the life of your application. This creates a root reference for any listeners of that event. Unfortunately, the workaround posted on the linked page did not seem to work very well for me. After modifying the workaround until it sufficiently suited my needs I found that the ToolStripTextBox control is not the only class that fails to unhook from this event causing leaks. For the project I'm working on this was causing a chain reaction of leaking objects that was fairly significant.

There are three ways to solve this problem that I can see. The first option is that you can try to predict the nature of the bug in the class that is leaking. Using this information you can code a very specific solution to this problem. The problem with this is that it requires that you are correct in your analysis of the problem which is buried in a class that you don't have the source code for and your targeted solution also works correctly. The second option I see here is the brute force method. Just unhook the method a bunch of times and hopefully the problem goes away. If I need to explain what's wrong with that don't waste your time reading further. The third option I see for solving this problem is to create a generic method that will look at the listeners of this event, find all references to the leaking object, and unhook them. This is the approach I have used to solve this problem.

To implement this solution I created a class UnhookSystemEventUserPreferenceChangedEvent. In this class there is a static public method UnhookObject(object pObjectToUnhook). This will take any object that is directly hooked (ToolStripTextBox and ToolStripItemOverflow are the two I've had problems with) to the Microsoft.Win32.SystemEvents.UserPreferenceChanged event and will unhook them. It's preferable to call this method in response to the disposing event of the leaking object. Rather than an abstract explanation of the code I've tried to comment the code itself as thoroughly as possible so that I could just post the code and let you walk through it. If there's another solution out there I didn't see it so for anyone who's been agonizing over this I hope this helps.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Win32;

namespace HelperClasses
{
     public class UnhookSystemEventUserPreferenceChangedEvent
     {
          //we'll use a static List to cache a reference to the internal list of UserPreferenceChangedEvent listeners so that
          // we do not need to search for it every time.
          static System.Collections.IList _UserPreferenceChangedList = null;

          static public void UnhookObject(object pObjectToUnhook)
          {
               //First check for null and get a ref to the UserPreferenceChangedEvent's internal list of listeners if needed.
               if (_UserPreferenceChangedList == null) GetUserPreferenceChangedList();
               //then, scan that list for any delegates that point to pObjectToUnhook.
               SearchListAndRemoveEventHandlers(pObjectToUnhook);
          }

          static private void GetUserPreferenceChangedList()
          {
               Type oSystemEventsType = typeof(SystemEvents);

               //Using reflection, get the FieldInfo object for the internal collection of handlers
               // we will use this collection to find the handler we want to unhook and remove it.
               // as you can guess by the naming convention it is a private member.
               System.Reflection.FieldInfo oFieldInfo = oSystemEventsType.GetField("_handlers",
                                   System.Reflection.BindingFlags.Static |
                                   System.Reflection.BindingFlags.GetField |
                                   System.Reflection.BindingFlags.FlattenHierarchy |
                                   System.Reflection.BindingFlags.NonPublic);

               //now, get a reference to the value of this field so that you can manipulate it.
               //pass null to GetValue() because we are working with a static member.
               object oFieldInfoValue = oFieldInfo.GetValue(null);

               //the returned object is of type Dictionary<object, List<SystemEventInvokeInfo>>
               //each of the Lists<> in the Dictionary<> is used to maintain a different event implementation.
               //It may be more efficient to figure out how the UserPreferenceChanged event is keyed here but a quick-and-dirty
               // method is to just scan them all the first time and then cache the List<> object once it's found.

               System.Collections.IDictionary dictFieldInfoValue = oFieldInfoValue as System.Collections.IDictionary;
               foreach (object oEvent in dictFieldInfoValue)
               {
                    System.Collections.DictionaryEntry deEvent = (System.Collections.DictionaryEntry)oEvent;
                    System.Collections.IList listEventListeners = deEvent.Value as System.Collections.IList;

                    //unfortunately, SystemEventInvokeInfo is a private class so we can't declare a reference of that type.
                    //we will use object and then use reflection to get what we need...
                    List<Delegate> listDelegatesToRemove = new List<Delegate>();

                    //we need to take the first item in the list, get it's delegate and check the type...
                    if (listEventListeners.Count > 0 && listEventListeners[0] != null)
                    {
                         Delegate oDelegate = GetDelegateFromSystemEventInvokeInfo(listEventListeners[0]);
                         if (oDelegate is UserPreferenceChangedEventHandler)
                         { _UserPreferenceChangedList = listEventListeners; }
                    }
                    //if we've found the list, no need to continue searching
                    if (_UserPreferenceChangedList != null) break;
               }
          }

          static private void SearchListAndRemoveEventHandlers(object pObjectToUnhook)
          {
               if (_UserPreferenceChangedList == null) return; //Do not run if we somehow haven't found the list.

               //unfortunately, SystemEventInvokeInfo is a private class so we can't declare a reference of that type.
               //we will use object and then use reflection to get what we need...
               List<UserPreferenceChangedEventHandler> listDelegatesToRemove = new List<UserPreferenceChangedEventHandler>();

               //this is NOT threadsafe. Unfortunately, if the collection is modified an exception will be thrown during iteration.
               // This will happen any time another thread hooks or unhooks the UserPreferenceChanged event while we iterate.
               // Modify this to be threadsafe somehow if that is required.
               foreach (object oSystemEventInvokeInfo in _UserPreferenceChangedList)
               {
                    UserPreferenceChangedEventHandler oDelegate =
                         GetDelegateFromSystemEventInvokeInfo(oSystemEventInvokeInfo) as UserPreferenceChangedEventHandler;

                    if (oDelegate != null && oDelegate.Target == pObjectToUnhook)
                    {
                         //at this point we have found an event handler that must be unhooked.
                         listDelegatesToRemove.Add(oDelegate);
                    }
               }

               //We should unhook using the public method because the internal implementation of this event is unknown.
               // iterating the private internal list is already shady enough without manipulating it directly...
               foreach (UserPreferenceChangedEventHandler itemToRemove in listDelegatesToRemove)
               { SystemEvents.UserPreferenceChanged -= itemToRemove; }
          }

          static private Delegate GetDelegateFromSystemEventInvokeInfo(object pSystemEventInvokeInfo)
          {
               Type typeSystemEventInvokeInfo = pSystemEventInvokeInfo.GetType();
               System.Reflection.FieldInfo oTmpFieldInfo = typeSystemEventInvokeInfo.GetField("_delegate",
                                   System.Reflection.BindingFlags.Instance |
                                   System.Reflection.BindingFlags.GetField |
                                   System.Reflection.BindingFlags.FlattenHierarchy |
                                   System.Reflection.BindingFlags.NonPublic);

               //Here we are NOT working with a static field so we will supply the SystemEventInvokeInfo
               // object that we found in the List<> object to the GetValue() function.
               Delegate oReturn = oTmpFieldInfo.GetValue(pSystemEventInvokeInfo) as Delegate;

               return oReturn;
          }
     }
}

32 comments:

  1. I see several issues in your class:

    1.I think GetUserPreferenceChangedList should be called each time when we call
    UnhookObject. You will miss all handlers that were hooked after setting _UserPreferenceChangedList to not null.

    2.Why in GetUserPreferenceChangedList do you use only listEventListeners[0]? What with other items? I think you miss handlers in this way.

    3.All methods are static so class also should be static.

    4.What with event: UserPreferenceChanging? It also might be problem of memory leak?

    ReplyDelete
  2. Jacek-
    for issues 1 and 2 the answer is pretty much the same. The private _handlers collection that is used internally within the SystemEvents object is a key:value dictionary that keeps a separate list for each event. We need to find that list for the UserPreferenceChanged event because that's the event that's not getting unhooked and is therefore the source of the problem. You can think of this list as you would the InvocationList of a multicast delegate. That being said, for issue #1 we don't need to scan for the list once we have a pointer to it and for item #2 we only need to test the first item in the list because all items in each list have the same delegate type. When we find a list that contains even 1 delegate of type "UserPreferenceChangedEventHandler" we can be sure that we've found the list we need.

    For issue #3 you're probably right :)

    Finally for issue #4 I'm sure that there's plenty of other issues with .net controls that I haven't covered and I'd be happy to provide suggestions for any problems you might encounter. If you find a leaking object that you can't get unhooked post the event and I can try to help :)

    ReplyDelete
  3. Ok, you have right :)
    I have not seen C# for two weeks…

    ReplyDelete
  4. Do you know if the same memory leak issue occurs when using Mono?

    ReplyDelete
    Replies
    1. This comment has been removed by the author.

      Delete
    2. I was searching for loan to sort out my bills& debts, then i saw comments about Blank ATM Credit Card that can be hacked to withdraw money from any ATM machines around you . I doubted thus but decided to give it a try by contacting (officialhackingcompany@gmail.com} they responded with their guidelines on how the card works. I was assured that the card can withdraw $5,000 instant per day & was credited with$50,000,000.00 so i requested for one & paid the delivery fee to obtain the card, after 24 hours later, i was shock to see the UPS agent in my resident with a parcel{card} i signed and went back inside and confirmed the card work's after the agent left. This is no doubts because i have the card & has made used of the card. This hackers are USA based hackers set out to help people with financial freedom!! Contact these email if you wants to get rich with this Via: officialhackingcompany@gmail.com website: https://official-hacking-company.jimdosite.com/

      Delete
  5. Can't say. I would imagine that there's similar problems but with different classes.

    ReplyDelete
    Replies
    1. I believe there is a flaw in the design here, that perhaps you can remedy. The code example is designed to work off of 'pObjectToUnhook'. However, pObjectToUnhook is NOT the target of the delegate that is failing to be released.
      the Type of the object not being released is ToolStripTextBox+ToolStripTextBoxControl. This is a private class type and a private instance, which means, that passing in to the UnhookObject the toolStripTextBox1 that is indirectly referenced via 'ownerItem' of the ToolSTripTextBoxControl class, will never yield a positive comparison on oDelegate.Target == pObjectToUnhook, because pObjectToUnhook == oDelegate.Target.ownerItem.

      Any comments on this?

      Delete
    2. Sorry for not noticing the comment but better late than never :). That is correct. For the class ToolStripTextBox you can pass a reference to the "UnhoookObject(object)" and it will not unhook. This was production code that was tested and worked. If I remember correctly there was a helper class that was used to manage the cleanup when the ToolStripTextBox triggered it's "Disposed" event. Using a memory profiler you should have not trouble getting yourself a workable reference to pass into the function. That should be the easy part. The working assumption of the post was that you already have been profiling memory and found troublesome references that are rooted. I tried to provide the general tool to get the hard part out of the way for you once you are at that point. I retested the code by copying and pasting, hooking said event, and then using the UnhookObject(object) function to unhook it. This worked. As a note, this applied to .net framework 3.5 if I recall. It was never stated in the original post.

      Delete
    3. Also, I've seen it noted somewhere that this bug has since been resolved. Possibly changing the target of the delegate in the process. At the time of the post I believe it to have been working as described but for sure, as a general solution the class provided in the post does work.

      Delete
  6. This comment has been removed by the author.

    ReplyDelete
  7. Is this really working for beginners like me and I am studying some coded, how it working tell me some details,what the preferences applied first,

    ReplyDelete
    Replies
    1. I'm not sure what you mean but yes it works. If you're a beginner then probably you don't do much memory profiling and quite honestly, you're probably not too worried about forms getting rooted. The production code where this solution was used had a requirement that it remain open without restarting indefinitely. For us it was a real problem to have disposed objects that the GC couldn't remove. It's very likely that you won't need to worry about it.

      Delete
  8. Hi Ray, many thanks for this. I have a leak and memory profiler is showing the UserPreferenceChangedEventHandler is pinning some objects that should be GC'd. Will try your solution.

    ReplyDelete
  9. A part of this code appears in s01e05 at 7:38 of the show Darknet.

    ReplyDelete
  10. All thanks to Elegant loan firm for helping me secure a loan of $1,000,000.00 USD to establish my Foodstuff supermarket business in different places. I have been looking for a financial help for the past four years. But now, am completely stressed free all the help of the loan officer Mr Russ Harry. So, I will advise any person who seek for funds to improve his or her business to contact this great firm for help, and it is real and tested. You can reach them through- Email --Elegantloanfirm@Hotmail.com-  or Whats-app +393511617486.

    ReplyDelete
  11. I want to share my testimony on how i got the blank ATM card. I was so wrecked that my company fired me simply because i did not obliged to their terms, so they hacked into my system and phone and makes it so difficult to get any other job, i did all i could but things kept getting worse by the day that i couldn’t afford my 3 kids fees and pay my bills. I owe so many people trying to borrow money to survive because my old company couldn’t allow me get another job and they did all they could to destroy my life just for declining to be among their evil deeds. haven’t given up i kept searching for job online when i came across the testimony of a lady called Judith regarding how she got the blank ATM card. Due to my present state, i had to get in touch with Hacker called OSCAR WHITE of oscarwhitehackersworld@gmail.com and he told me the procedures and along with the terms which i agreed to abide and i was told that the Blank card will be deliver to me without any further delay and i hold on to his words and to my greatest surprise, i received an ATM card worth $4.5 million USD , All Thanks to OSCAR WHITE , if you are facing any financial problem contact him asap email address is oscarwhitehackersworld@gmail.com or whats-app +1(323)-362-2310

    ReplyDelete

  12. Cool way to have financial freedom!!! Are you tired of living a poor life, here is the opportunity you have been waiting for. Get the new ATM BLANK CARD that can hack any ATM MACHINE and withdraw money from any account. You do not require anybody’s account number before you can use it. Although you and I knows that its illegal,there is no risk using it. It has SPECIAL FEATURES, that makes the machine unable to detect this very card,and its transaction can’t be traced .You can use it anywhere in the world. With this card,you can withdraw nothing less than $4,500 a day. So to get the card,reach the hackers via email address : besthackersworld58@gmail.com or whatsapp him on +1(323)-723-2568

    ReplyDelete
  13. I was in a relationship with Mark for about 3years. I was so true to him i had plans to marry him someday….soon. Then I started noticing some foul play. he always tried to satisfy me even when I wanted only little of him. A sign he was cheating so I decided to take matters in my hand and told my best friend about it. He gave me someone’s contact who changed my whole life for the better. thought it was a joke after when i funded the exploits and told to be in 24 hours, He helped me hack his FB account,his emails and I got to find out he had been cheating with not one but different women since we’ve been together. All Thanks to onlineghosthacker247 get to him on (onlineghosthacker247@gmail.com) you gonna thank me later!!

    ReplyDelete
  14. HOW I GO MY DESIRED LOAN AMOUNT FROM A RELIABLE AND TRUSTED LOAN COMPANY LAST WEEK. Email for immediate response: drbenjaminfinance@gmail.com Call/Text: +1(415)630-7138 Whatsapp +19292227023

    Hello everyone, My name is Mr.Justin Riley Johnson, I am from Texas, United State, am here to testify of how i got my loan from BENJAMIN LOAN INVESTMENTS FINANCE(drbenjaminfinance@gmail.com) after i applied Two times from various loan lenders who claimed to be lenders right here this forum,i thought their lending where real and i applied but they never gave me loan until a friend of mine introduce me to {Dr.Benjamin Scarlet Owen} the C.E.O of BENJAMIN LOAN INVESTMENTS FINANCE who promised to help me with a loan of my desire and he really did as he promised without any form of delay, I never thought there are still reliable loan lenders until i met {Dr.Benjamin Scarlet Owen}, who really helped me with my loan and changed my life for the better. I don't know if you are in need of an urgent loan also, So feel free to contact Dr.Benjamin Scarlet Owen on his email address: drbenjaminfinance@gmail.com BENJAMIN LOAN INVESTMENTS FINANCE holds all of the information about how to obtain money quickly and painlessly via Whatsapp +19292227023 Email: drbenjaminfinance@gmail.com and consider all your financial problems tackled and solved. Share this to help a soul right now, Thanks..

    ReplyDelete
  15. I want to share my testimony on how i got the blank ATM card. I was so wrecked that my company fired me simply because i did not obliged to their terms, so they hacked into my system and phone and makes it so difficult to get any other job, i did all i could but things kept getting worse by the day that i couldn’t afford my 3 kids fees and pay my bills. I owe so many people trying to borrow money to survive because my old company couldn’t allow me get another job and they did all they could to destroy my life just for declining to be among their evil deeds. haven’t given up i kept searching for job online when i came across the testimony of a lady called Judith regarding how she got the blank ATM card. Due to my present state, i had to get in touch with Hacker called OSCAR WHITE of oscarwhitehackersworld@gmail.com and he told me the procedures and along with the terms which i agreed to abide and i was told that the Blank card will be deliver to me without any further delay and i hold on to his words and to my greatest surprise, i received an ATM card worth $4.5 million USD , All Thanks to OSCAR WHITE , if you are facing any financial problem contact him asap email address is oscarwhitehackersworld@gmail.com or whats-app +1(323)-362-2310

    ReplyDelete
  16. I was searching for a loan to sort out my bills& debts, then I saw comments about Blank ATM Credit Cards that can be hacked to withdraw money from any ATM machines around you . I doubted thus but decided to give it a try by contacting (smithhackingcompanyltd@gmail.com} they responded with their guidelines on how the card works. I was assured that the card can withdraw $5,000 instant per day & was credited with$50,000,000.00 so i requested for one & paid the delivery fee to obtain the card, after 24 hours later, i was shock to see the UPS agent in my resident with a parcel{card} i signed and went back inside and confirmed the card work after the agent left. This is no doubt because I have the card & have made use of the card. These hackers are USA based hackers set out to help people with financial freedom!! Contact these email if you wants to get rich with this Via: smithhackingcompanyltd@gmail.com 

    ReplyDelete

  17. My Name is Eric Morgan , I was searching for loan to sort out my bills& debts, then i saw comments about Blank ATM Credit Card that can be hacked to withdraw money from any ATM machines around you . I doubted thus but decided to give it a try by contacting oscarwhitehackersworld@gmail.com or whats-app +1(323)-362-2310 they responded with their guidelines on how the card works. I was assured that the card can withdraw $4,500 instant per day and also carry out online purchase with the card , so i requested for one & paid the delivery fee to obtain the card, after 24 hours later, i was shock to see the UPS agent in my resident with a parcel{card} i signed and went back inside and confirmed the card work's after the agent left. This is no doubts because i have the card & has made used of the card. This hackers are USA based hackers set out to help people with financial freedom,contact Mr Oscar white and gain your financail freedom : oscarwhitehackersworld@gmail.com or whats-app +1(323)-362-2310

    ReplyDelete
  18. My name is Jane Wembli Josh and i live in the USA California and life is worth living right now for me and my family and all this is because of one man sent by GOD to help me and my family, i once had a life filled with sorrow because my first SON needed a kidney transplant and all our savings were going towards his medications and this normally leaves us with no money to pay our bills or even put enough food on our table and our rent was due and no funds to pay these bills and life felt so unfair to me and every night my wife will cry herself to sleep every night until one day, i was browsing through yahoo answers and i saw a striking advert of a man that gives out personal loans and that the offer is opened to all and i have heard so many things about internet scams but at this point of my life, i was very desperate and ready to take any risk and at the end of the day, i applied for this loan and from one step to another, i got my loan within 12 hours through bank transfer and you know, it was all like a dream and i called Rev. Fr. Kevin Doran A Man who is the GOD sent lender i found and said, i have received my loan and he smiled stating that to GOD be the glory and i was so shocked as i have never ever seen anyone with such a GOD fearing and kind heart and today, i am the happiest man on earth because by GOD’S grace, my SON kidney transplant was successful and today he is healthy, i and my family are living very comfortable and happy and if you are in my former situation or in serious and legitimate need of a loan, you can reach this GOD sent lender via consumerloanfirm@gmail.com

    ReplyDelete
  19. DO YOU NEED AN URGENT LOAN???
    INSTANT AFFORDABLE PERSONAL/BUSINESS/HOME/INVESTMENT LOAN OFFER WITHOUT COST/STRESS CONTACT US TODAY VIA Whatsapp +19292227023 Email drbenjaminfinance@gmail.com

    Hello, Do you need an urgent loan to support your business or in any purpose? we are certified and legitimate and international licensed loan Company. We offer loans to Business firms, companies and individuals at an affordable interest rate of 2% , It might be a short or long term loan or even if you have poor credit, we shall process your loan as soon as we receive your application. we are an independent financial institution. We have built up an excellent reputation over the years in providing various types of loans to thousands of our customers. We Offer guaranteed loan services of any amount to people all over the globe, we offer easy Personal loans,Commercial/business loan, Car Loan Leasing/equipment finance, Debt consolidation loan, Home loan, ETC with either a good or bad credit history. If you are in need of a loan do contact us via Whatsapp +19292227023 Email drbenjaminfinance@gmail.com
    ®Capital Managements Inc™ 2021.
    Share this to help a soul right now, Thanks

    ReplyDelete
  20. Hello viewers all over the world, There is good news for you all today get your Blank ATM card that works in all ATM machines all over the world. We have specially programmed ATM cards that can be used to hack ATM machines, the ATM cards can be used to withdraw at the ATM or swipe, at stores and POS. We give out this cards to all interested clients worldwide, We give out THE Blank ATM Card. Do you want to live a good life thought its illegal, its the easiest way to be a millionaire. it also has a technique that makes it impossible for the CCTV to detect you and you can only withdraw a total amount of $5,000 Dollars in a day on ATM Machine also avaialbel at cash delivery. We give up to $10,000.00 to $1,000,000.00 Dollars With our network hacking services. We can Recover all your lost money to Bitcoin and other Crypto currency, mortgage/realestate scams and fake ICOs within 48 hours or less. (Thomas Freddie Hackers) working together as a team to track down & to recover funds back from the most difficult internet SCAMMERS. NOTE!! We've received countless heartbreaking reports of notorious scammers and we’ve successful recovery them back via thomasunlimitedhackers@gmail.com

    Do contact us on ((Binary Recovery. University Grades.Wiping Criminal Records, FB & IG Hack, Telegram, Loads & Phone Hacking)) border us with your jobs & allow us give you positive result with our hacking skills. We are certified and your privacy is 100% safe with us. Worry no more about your financial problems, If you are in need of any other cyber hack services, we are here for you anytime, any day so contact us via our Email Address: thomasunlimitedhackers@gmail.com

    Regards
    THOMAS FREDDIE UNLIMITED HACKERS
    Email thomasunlimitedhackers@gmail.com
    Call/Text: +1 (985)465-8370
    Motto: We offer the fastest and reliable services

    ReplyDelete
  21. I hacked my ex wife iPhone 12 pro max with the best verifiedprohackers@gmail.com and till now I am still inside her phone monitoring her calls, text messages, deleted text message, Whatsapp, Facebook, iMessage and many more and till all this are done without any form of trace is this hacker not great??? Thank you once again verifiedprohackers@gmail.com

    ReplyDelete
  22. INSTEAD OF GETTING A LOAN Check out these blank ATM cards today!!

    My name is Oliver Grey from New York. A successful business owner and father. I got one of these already programmed blank ATM cards that allows me withdraw a maximum of $5,000 daily for 30 days. I am so happy about these cards because I received mine last week and have already used it to get $20,000. Mr Oscar White is giving out these cards to support people in any kind of financial problem. I must be sincere to you, when i first saw the advert, I believed it to be illegal and a hoax but when I contacted Mr Oscar White, he confirmed to me that although it is illegal, nobody gets caught while using these cards because they have been programmed to disable every communication once inserted into any Automated Teller Machine(ATM). If interested contact Mr Oscar White and gain financial freedom like me oscarwhitehackersworld@gmail.com or whats-app +1(513)-299-8247 as soon as possible .

    God Bless

    ReplyDelete
  23. HELLO, I am Rebecca Michaelson by name living in Europe. Here is a good news for those interested. There is away you can earn money without stress contact (THOMAS FREDDIE) for a blank [ATM CARD] today and be among the lucky once who are benefiting from this cards. This PROGRAMMED blank ATM card is capable of hacking into any ATM machine anywhere in the world. I got my master card from a good Hacker on the internet, with this ATM Card I am able to collect $5000 dollars every day via contacts:
    +1 (985)-465-8370 {thomasunlimitedhackers@gmail.com}
    I was very poor but this card have made me rich and happy, If you want to get this opportunity to become rich and establish your business then apply for this Master card, I am so happy about this because i got mine last week and I have used it to get $240,000.00 dollars from THOMAS FREDDIE UNLIMITED Hackers is giving out the card just to help the poor and needy and they ALSO OFFER FINANCIAL ASSISTANCE. get yours from THOMAS FREDDIE UNLIMITED HACKERS today. Kindly contact them by Email thomasunlimitedhackers@gmail.com

    Thank You and God bless

    ReplyDelete
  24. I am sure a lot of us are still unaware of the recent development of the Blank ATM card.. An ATM card that can change your financial status within a few days. With this Blank ATM card, you can withdraw between $1,000-$5,000 daily from any ATM machine in the world. There is no risk of getting caught by any form of security if you followed the instructions properly. The Blank ATM card is also sophisticated due to the fact that the card has its own security making your transaction very safe and untraceable. For more info contact Mr Calvin Grayson via email: officialblankatmservice@gmail.com or whatsApp +447937001817

    ReplyDelete
  25. Programmed ATM Cards
    Do you know that you can hack any ATM machine !!!
    We have specially programmed ATMs that can be used to withdraw money at ATMs, shops and points of sale. We sell these cards to all our customers and interested buyers all over the world, the cards have a withdrawal limit every week.
    Getting rich and living the rich and famous lifestyle is a dream of many people. And while most people go to work or look for other ethical methods to make money on ATM-programmed cards.
    The programmed ATMs withdraw money from each ATM but have a withdrawal limit every week, only your PIN code is in it, it is a high-tech card system. The PROGRAMMED ATM card works on all card-based ATMs, anywhere in the world.
    Email: atmservices44@aol.com
    Email: hacklords.investors@gmail.com

    ReplyDelete