blob: 7b93e0cd50a288049e2e989f330d21ea21200d94 [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include <vector>
#include <utility>
#include <sstream>
#include <ts/ts.h>
#include "tscpp/util/TextView.h"
#include "tscpp/api/Continuation.h"
// TSReleaseAssert() doesn't seem to produce any logging output for a debug build, so do both kinds of assert.
//
#define ALWAYS_ASSERT(EXPR) \
{ \
TSAssert(EXPR); \
TSReleaseAssert(EXPR); \
}
std::vector<void (*)()> testList;
struct ATest {
ATest(void (*testFuncPtr)()) { testList.push_back(testFuncPtr); }
};
// Put a test function, whose name is the actual parameter for TEST_FUNC, into testList, the list of test functions.
//
#define TEST(TEST_FUNC) ATest t(TEST_FUNC);
// TextView test. This is not testing the actual TextView code, just that it works to call functions in TextView.cc in the core
// from a plugin.
//
namespace TextViewTest
{
void
f()
{
ts::TextView tv("abcdefg");
std::ostringstream oss;
oss << tv;
ALWAYS_ASSERT(ts::memcmp(ts::TextView(oss.str()), tv) == 0)
}
TEST(f)
} // end namespace TextViewTest
// Test for Continuation class.
//
namespace ContinuationTest
{
struct {
TSEvent event;
void *edata;
} passedToEventFunc;
bool
checkPassed(TSEvent event, void *edata)
{
return (passedToEventFunc.event == event) and (passedToEventFunc.edata == edata);
}
class TestCont : public atscppapi::Continuation
{
public:
TestCont(Mutex m) : atscppapi::Continuation(m) {}
TestCont() = default;
private:
int
_run(TSEvent event, void *edata) override
{
passedToEventFunc.event = event;
passedToEventFunc.edata = edata;
return 666;
}
};
void
f()
{
TestCont::Mutex m(TSMutexCreate());
TestCont c(m);
ALWAYS_ASSERT(!!c)
ALWAYS_ASSERT(c.asTSCont() != nullptr)
ALWAYS_ASSERT(c.mutex() == m)
TestCont c2(std::move(c));
ALWAYS_ASSERT(!!c2)
ALWAYS_ASSERT(c2.asTSCont() != nullptr)
ALWAYS_ASSERT(c2.mutex() == m)
ALWAYS_ASSERT(!c)
ALWAYS_ASSERT(c.asTSCont() == nullptr)
ALWAYS_ASSERT(c.mutex() == nullptr)
TestCont c3;
ALWAYS_ASSERT(!c3)
ALWAYS_ASSERT(c3.asTSCont() == nullptr)
ALWAYS_ASSERT(c3.mutex() == nullptr)
c3 = std::move(c2);
ALWAYS_ASSERT(!!c3)
ALWAYS_ASSERT(c3.asTSCont() != nullptr)
ALWAYS_ASSERT(c3.mutex() == m)
ALWAYS_ASSERT(!c2)
ALWAYS_ASSERT(c2.asTSCont() == nullptr)
ALWAYS_ASSERT(c2.mutex() == nullptr)
c3.destroy();
ALWAYS_ASSERT(!c3)
ALWAYS_ASSERT(c3.asTSCont() == nullptr)
ALWAYS_ASSERT(c3.mutex() == nullptr)
c = TestCont(m);
ALWAYS_ASSERT(!!c)
ALWAYS_ASSERT(c.asTSCont() != nullptr)
ALWAYS_ASSERT(c.mutex() == m)
ALWAYS_ASSERT(c.call(TS_EVENT_INTERNAL_206) == 666)
ALWAYS_ASSERT(checkPassed(TS_EVENT_INTERNAL_206, nullptr))
int dummy;
ALWAYS_ASSERT(c.call(TS_EVENT_INTERNAL_207, &dummy) == 666)
ALWAYS_ASSERT(checkPassed(TS_EVENT_INTERNAL_207, &dummy))
}
TEST(f)
} // end namespace ContinuationTest
// Run all the tests.
//
void
TSPluginInit(int, const char **)
{
TSPluginRegistrationInfo info;
info.plugin_name = "test_cppapi";
info.vendor_name = "Apache Software Foundation";
info.support_email = "dev@trafficserver.apache.org";
ALWAYS_ASSERT(TSPluginRegister(&info) == TS_SUCCESS)
for (auto fp : testList) {
fp();
}
}