| Index: compiled/subscription/DownloadableSubscription.cpp |
| =================================================================== |
| --- a/compiled/subscription/DownloadableSubscription.cpp |
| +++ b/compiled/subscription/DownloadableSubscription.cpp |
| @@ -10,26 +10,172 @@ |
| * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| * GNU General Public License for more details. |
| * |
| * You should have received a copy of the GNU General Public License |
| * along with Adblock Plus. If not, see <http://www.gnu.org/licenses/>. |
| */ |
| +#include <cwctype> |
| + |
| #include "DownloadableSubscription.h" |
| +#include "../FilterNotifier.h" |
| +#include "../StringScanner.h" |
| +#include "../filter/CommentFilter.h" |
| + |
| +namespace { |
| + constexpr int MILLIS_IN_HOUR = 60 * 60 * 1000; |
| + constexpr int MILLIS_IN_DAY = 24 * MILLIS_IN_HOUR; |
| +} |
| + |
| +_DownloadableSubscription_Parser::_DownloadableSubscription_Parser(DownloadableSubscription& sub) |
| + : mSubscription(&sub) |
| +{ |
| +} |
| + |
| +void _DownloadableSubscription_Parser::Process(DependentString& line) |
| +{ |
| + auto filter = FilterPtr(Filter::FromText(line), false); |
| + if (filter->mType == Filter::Type::COMMENT) |
| + { |
| + auto comment = filter->As<CommentFilter>(); |
| + if (!comment->GetParam().empty()) |
| + { |
| + if (comment->GetParam() == u"checksum"_str) |
| + { |
| + // XXX we'll have to calculate the checksum. |
|
hub
2017/11/13 22:35:27
this part will require import a md5sum calculation
|
| + } |
| + mParams[comment->GetParam()] = comment->GetValue(); |
| + } |
| + } |
| + |
| + if (filter) |
| + mFilters.push_back(filter); |
| +} |
| + |
| +int _DownloadableSubscription_Parser::ParseExpires(const String& expires) |
| +{ |
| + bool isHour = false; |
| + StringScanner scanner(expires); |
| + String::size_type numStart = 0; |
| + String::size_type numLen = 0; |
| + while(!scanner.done()) |
| + { |
| + auto ch = scanner.next(); |
| + if (std::iswdigit(ch)) |
| + { |
| + if (numLen == 0) |
| + numStart = scanner.position(); |
| + numLen++; |
| + } |
| + else if (std::iswspace(ch)) |
| + { |
| + if (numLen) |
| + break; |
| + } |
| + else |
| + { |
| + if (numLen) |
| + scanner.back(); |
| + break; |
| + } |
| + } |
| + |
| + DependentString numStr(expires, numStart, numLen); |
| + int num = numStr.toInt(); |
| + if (num == 0) |
| + return 0; |
| + |
| + while (!scanner.done()) |
| + { |
| + auto ch = scanner.next(); |
| + if (std::iswspace(ch)) |
| + continue; |
| + if (ch == u'h') |
| + { |
| + isHour = true; |
| + // assume we are done here. The rest is ignored. |
| + break; |
| + } |
| + } |
| + // check for overflow. |
| + if (!isHour && num > 24) |
|
hub
2017/11/13 22:35:27
I should check the overflow for the expiration in
|
| + return 0; |
| + |
| + num *= isHour ? MILLIS_IN_HOUR : MILLIS_IN_DAY; |
| + return num; |
| +} |
| + |
| +int _DownloadableSubscription_Parser::Finalize() |
| +{ |
| + auto entry = mParams.find(u"title"_str); |
| + if (entry) |
| + { |
| + mSubscription->SetTitle(entry->second); |
| + mSubscription->SetFixedTitle(true); |
| + } |
| + else |
| + mSubscription->SetFixedTitle(false); |
| + |
| + int version = 0; |
| + entry = mParams.find(u"version"_str); |
| + if (entry) |
| + version = entry->second.toInt(); |
| + mSubscription->SetDataRevision(version); |
| + |
| + int expires = 0; |
| + entry = mParams.find(u"expires"_str); |
| + if (entry) |
| + expires = ParseExpires(entry->second); |
| + |
| + FilterNotifier::SubscriptionChange( |
| + FilterNotifier::Topic::SUBSCRIPTION_BEFORE_FILTERS_REPLACED, |
| + *mSubscription); |
|
hub
2017/11/13 22:35:28
I'm not if that's the right place to send this not
|
| + auto oldFilters = std::move(mSubscription->GetFilters()); |
| + mSubscription->GetFilters() = std::move(mFilters); |
| + FilterNotifier::SubscriptionChange( |
| + FilterNotifier::Topic::SUBSCRIPTION_FILTERS_REPLACED, *mSubscription); |
| + |
| + return expires; |
| +} |
| + |
| +namespace { |
| + DependentString emptyString = u""_str; |
| +} |
| + |
| +const String& _DownloadableSubscription_Parser::GetRedirect() const |
| +{ |
| + auto entry = mParams.find(u"redirect"_str); |
| + if (entry) |
| + return entry->second; |
| + return emptyString; |
| +} |
| + |
| +const String& _DownloadableSubscription_Parser::GetHomepage() const |
| +{ |
| + auto entry = mParams.find(u"homepage"_str); |
| + if (entry) |
| + return entry->second; |
| + return emptyString; |
| +} |
| DownloadableSubscription::DownloadableSubscription(const String& id) |
| : Subscription(classType, id), mFixedTitle(false), mLastCheck(0), |
| mHardExpiration(0), mSoftExpiration(0), mLastDownload(0), mLastSuccess(0), |
| mErrorCount(0), mDataRevision(0), mDownloadCount(0) |
| { |
| SetTitle(id); |
| } |
| +_DownloadableSubscription_Parser* DownloadableSubscription::ParseDownload() |
| +{ |
| + return new _DownloadableSubscription_Parser(*this); |
| +} |
| + |
| OwnedString DownloadableSubscription::Serialize() const |
| { |
| OwnedString result(Subscription::Serialize()); |
| if (mFixedTitle) |
| result.append(u"fixedTitle=true\n"_str); |
| if (!mHomepage.empty()) |
| { |
| result.append(u"homepage="_str); |