mirror of
https://github.com/scp-fs2open/fs2open.github.com.git
synced 2026-11-08 17:48:46 -10:00
* Add automatic lua obj serialization function dispatch * Implement fundamental and object de/serialization * Proper default case for package deserialization * Add No Multi func * Add Serialization part * Fix max encoding size for userdata * Implement exception handling * Start Implementing lua RPC * Prepare waitAsync for RPC * Add packet order enforcing and forwarding * Add RPC registry * Make RPCs callable * Add waitRPC * Add serializers * Fix GCC error * Explicitly specify lua_net_exception * Fix Warnings * Replace Seriliaze fundamental with cross-platform data types * Appease Clang * Prevent serialization CTD on invalid objects * Actually use the temporaries assigned * Fix OSWPT shadow * Fix table deserialize order * Incorporate Feedback * Fix Warnigs * ix WArnings 2 * Add sanity checks for OSWPT wing serialization * Multi Bump * Forgot we have american-style dates there
284 lines
8.4 KiB
C++
284 lines
8.4 KiB
C++
//
|
|
//
|
|
|
|
#include "oswpt.h"
|
|
#include "parse_object.h"
|
|
#include "ship.h"
|
|
#include "team.h"
|
|
#include "waypoint.h"
|
|
#include "wing.h"
|
|
#include "ship/ship.h"
|
|
#include "mission/missionparse.h"
|
|
|
|
#include "network/multi.h"
|
|
#include "network/multimsgs.h"
|
|
#include "network/multiutil.h"
|
|
|
|
void object_ship_wing_point_team::serialize(lua_State* /*L*/, const scripting::ade_table_entry& /*tableEntry*/, const luacpp::LuaValue& value, ubyte* data, int& packet_size) {
|
|
object_ship_wing_point_team oswpt;
|
|
value.getValue(scripting::api::l_OSWPT.Get(&oswpt));
|
|
uint8_t oswpttype = static_cast<uint8_t>(oswpt.type);
|
|
ADD_DATA(oswpttype);
|
|
switch (oswpt.type) {
|
|
case oswpt_type::SHIP:
|
|
case oswpt_type::WAYPOINT:
|
|
ADD_USHORT(oswpt.objp->net_signature);
|
|
break;
|
|
case oswpt_type::PARSE_OBJECT:
|
|
ADD_USHORT(oswpt.ship_entry->p_objp->net_signature);
|
|
break;
|
|
case oswpt_type::WING:
|
|
case oswpt_type::WING_NOT_PRESENT: {
|
|
int wingidx = WING_INDEX(oswpt.wingp);
|
|
ADD_INT(wingidx);
|
|
break;
|
|
}
|
|
case oswpt_type::SHIP_ON_TEAM:
|
|
case oswpt_type::WHOLE_TEAM:
|
|
ADD_INT(oswpt.team);
|
|
break;
|
|
case oswpt_type::NONE:
|
|
case oswpt_type::EXITED:
|
|
default:
|
|
break;
|
|
}
|
|
}
|
|
|
|
void object_ship_wing_point_team::deserialize(lua_State* /*L*/, const scripting::ade_table_entry& /*tableEntry*/, char* data_ptr, ubyte* data, int& offset) {
|
|
uint8_t oswpttype;
|
|
GET_DATA(oswpttype);
|
|
switch (static_cast<oswpt_type>(oswpttype)) {
|
|
case oswpt_type::SHIP:
|
|
case oswpt_type::WAYPOINT: {
|
|
ushort net_signature;
|
|
GET_USHORT(net_signature);
|
|
object_ship_wing_point_team oswpt;
|
|
oswpt.type = static_cast<oswpt_type>(oswpttype);
|
|
//This doesn't constitute a valid waypoint oswpt, but it will work for everything that lua has access to, so it's fine
|
|
oswpt.objp = multi_get_network_object(net_signature);
|
|
new(data_ptr) object_ship_wing_point_team(std::move(oswpt));
|
|
break;
|
|
}
|
|
case oswpt_type::PARSE_OBJECT: {
|
|
ushort net_signature;
|
|
GET_USHORT(net_signature);
|
|
new(data_ptr) object_ship_wing_point_team(mission_parse_get_arrival_ship(net_signature));
|
|
break;
|
|
}
|
|
case oswpt_type::WING:
|
|
case oswpt_type::WING_NOT_PRESENT: {
|
|
int wingidx;
|
|
GET_INT(wingidx);
|
|
if((wingidx < 0) || (wingidx >= Num_wings) || (Wings[wingidx].num_waves == -1))
|
|
new(data_ptr) object_ship_wing_point_team;
|
|
else
|
|
new(data_ptr) object_ship_wing_point_team(&Wings[wingidx]);
|
|
break;
|
|
}
|
|
case oswpt_type::SHIP_ON_TEAM:
|
|
case oswpt_type::WHOLE_TEAM: {
|
|
int oswpt_team;
|
|
GET_INT(oswpt_team);
|
|
object_ship_wing_point_team oswpt;
|
|
oswpt.team = oswpt_team;
|
|
oswpt.type = static_cast<oswpt_type>(oswpttype);
|
|
new(data_ptr) object_ship_wing_point_team(std::move(oswpt));
|
|
break;
|
|
}
|
|
case oswpt_type::NONE:
|
|
case oswpt_type::EXITED:
|
|
default:
|
|
new(data_ptr) object_ship_wing_point_team;
|
|
break;
|
|
}
|
|
}
|
|
|
|
|
|
|
|
#define OSWPT_TYPE_NONE oswpt_type::NONE
|
|
#define OSWPT_TYPE_SHIP oswpt_type::SHIP
|
|
#define OSWPT_TYPE_WING oswpt_type::WING
|
|
#define OSWPT_TYPE_WAYPOINT oswpt_type::WAYPOINT
|
|
#define OSWPT_TYPE_SHIP_ON_TEAM oswpt_type::SHIP_ON_TEAM
|
|
#define OSWPT_TYPE_WHOLE_TEAM oswpt_type::WHOLE_TEAM
|
|
#define OSWPT_TYPE_PARSE_OBJECT oswpt_type::PARSE_OBJECT
|
|
#define OSWPT_TYPE_EXITED oswpt_type::EXITED
|
|
#define OSWPT_TYPE_WING_NOT_PRESENT oswpt_type::WING_NOT_PRESENT
|
|
|
|
|
|
namespace scripting {
|
|
namespace api {
|
|
|
|
//**********HANDLE: Wing
|
|
ADE_OBJ(l_OSWPT, object_ship_wing_point_team, "oswpt", "Handle for LuaSEXP arguments that can hold different types (Object/Ship/Wing/Waypoint/Team)");
|
|
|
|
ADE_FUNC(getType, l_OSWPT, nullptr, "The data-type this OSWPT yields on the get method.", "string", "The name of the data type. Either 'ship', 'parseobject' (a yet-to-spawn ship), 'wing' (can include yet-to-arrive wings with 0 current ships), 'team' (both explicit and ship-on-team), 'waypoint', or 'none' (either explicitly specified, a ship that doesn't exist anymore, or invalid OSWPT object).")
|
|
{
|
|
object_ship_wing_point_team oswpt;
|
|
if (!ade_get_args(L, "o", l_OSWPT.Get(&oswpt)))
|
|
return ade_set_error(L, "s", "none");
|
|
|
|
switch (oswpt.type) {
|
|
case OSWPT_TYPE_SHIP:
|
|
return ade_set_args(L, "s", "ship");
|
|
case OSWPT_TYPE_PARSE_OBJECT:
|
|
return ade_set_args(L, "s", "parseobject");
|
|
case OSWPT_TYPE_WING:
|
|
case OSWPT_TYPE_WING_NOT_PRESENT:
|
|
return ade_set_args(L, "s", "wing");
|
|
case OSWPT_TYPE_SHIP_ON_TEAM:
|
|
case OSWPT_TYPE_WHOLE_TEAM:
|
|
return ade_set_args(L, "s", "team");
|
|
case OSWPT_TYPE_WAYPOINT:
|
|
return ade_set_args(L, "s", "waypoint");
|
|
case OSWPT_TYPE_NONE:
|
|
case OSWPT_TYPE_EXITED:
|
|
default:
|
|
return ade_set_args(L, "s", "none");
|
|
}
|
|
}
|
|
|
|
ADE_FUNC(get, l_OSWPT, nullptr, "Returns the data held by this OSWPT.", "ship | parse_object | wing | team | waypoint | nil", "Returns the data held by this OSWPT, nil if type is 'none'.")
|
|
{
|
|
object_ship_wing_point_team oswpt;
|
|
if (!ade_get_args(L, "o", l_OSWPT.Get(&oswpt)))
|
|
return ADE_RETURN_NIL;
|
|
|
|
switch (oswpt.type) {
|
|
case OSWPT_TYPE_SHIP:
|
|
return ade_set_args(L, "o", l_Ship.Set(object_h(oswpt.objp)));
|
|
case OSWPT_TYPE_PARSE_OBJECT:
|
|
return ade_set_args(L, "o", l_ParseObject.Set(parse_object_h(oswpt.ship_entry->p_objp)));
|
|
case OSWPT_TYPE_WING:
|
|
case OSWPT_TYPE_WING_NOT_PRESENT:
|
|
return ade_set_args(L, "o", l_Wing.Set(WING_INDEX(oswpt.wingp)));
|
|
case OSWPT_TYPE_SHIP_ON_TEAM:
|
|
case OSWPT_TYPE_WHOLE_TEAM:
|
|
return ade_set_args(L, "o", l_Team.Set(oswpt.team));
|
|
case OSWPT_TYPE_WAYPOINT:
|
|
return ade_set_args(L, "o", l_Waypoint.Set(object_h(oswpt.objp)));
|
|
case OSWPT_TYPE_NONE:
|
|
case OSWPT_TYPE_EXITED:
|
|
default:
|
|
return ADE_RETURN_NIL;
|
|
}
|
|
}
|
|
|
|
ADE_FUNC(forAllShips, l_OSWPT, "function(ship ship) => void body", "Applies this function to each (present) ship this OSWPT applies to.", nullptr, nullptr)
|
|
{
|
|
object_ship_wing_point_team oswpt;
|
|
luacpp::LuaFunction body;
|
|
if (!ade_get_args(L, "ou", l_OSWPT.Get(&oswpt), &body))
|
|
return ADE_RETURN_NIL;
|
|
|
|
switch (oswpt.type) {
|
|
case OSWPT_TYPE_SHIP:
|
|
{
|
|
luacpp::LuaValueList args;
|
|
args.push_back(luacpp::LuaValue::createValue(L, l_Ship.Set(object_h(oswpt.objp))));
|
|
|
|
body.call(L, args);
|
|
break;
|
|
}
|
|
case OSWPT_TYPE_WING:
|
|
{
|
|
auto wp = oswpt.wingp;
|
|
for (int i = 0; i < wp->current_count; ++i)
|
|
{
|
|
luacpp::LuaValueList args;
|
|
args.push_back(luacpp::LuaValue::createValue(L, l_Ship.Set(object_h(&Objects[Ships[wp->ship_index[i]].objnum]))));
|
|
|
|
body.call(L, args);
|
|
}
|
|
break;
|
|
}
|
|
case OSWPT_TYPE_SHIP_ON_TEAM:
|
|
case OSWPT_TYPE_WHOLE_TEAM:
|
|
for (auto so = GET_FIRST(&Ship_obj_list); so != END_OF_LIST(&Ship_obj_list); so = GET_NEXT(so))
|
|
{
|
|
if (Objects[so->objnum].flags[Object::Object_Flags::Should_be_dead])
|
|
continue;
|
|
|
|
if (Ships[Objects[so->objnum].instance].team == oswpt.team)
|
|
{
|
|
luacpp::LuaValueList args;
|
|
args.push_back(luacpp::LuaValue::createValue(L, l_Ship.Set(object_h(&Objects[so->objnum]))));
|
|
|
|
body.call(L, args);
|
|
}
|
|
}
|
|
break;
|
|
case OSWPT_TYPE_PARSE_OBJECT:
|
|
case OSWPT_TYPE_WING_NOT_PRESENT:
|
|
case OSWPT_TYPE_WAYPOINT:
|
|
case OSWPT_TYPE_NONE:
|
|
case OSWPT_TYPE_EXITED:
|
|
default:
|
|
break;
|
|
}
|
|
|
|
return ADE_RETURN_NIL;
|
|
}
|
|
|
|
|
|
ADE_FUNC(forAllParseObjects, l_OSWPT, "function(parse_object po) => void body", "Applies this function to each not-yet-present ship (includes not-yet-present wings and not-yet-present ships of a specified team!) this OSWPT applies to.", nullptr, nullptr)
|
|
{
|
|
object_ship_wing_point_team oswpt;
|
|
luacpp::LuaFunction body;
|
|
if (!ade_get_args(L, "ou", l_OSWPT.Get(&oswpt), &body))
|
|
return ADE_RETURN_NIL;
|
|
|
|
switch (oswpt.type) {
|
|
case OSWPT_TYPE_PARSE_OBJECT:
|
|
{
|
|
luacpp::LuaValueList args;
|
|
args.push_back(luacpp::LuaValue::createValue(L, l_ParseObject.Set(parse_object_h(oswpt.ship_entry->p_objp))));
|
|
|
|
body.call(L, args);
|
|
break;
|
|
}
|
|
case OSWPT_TYPE_WING_NOT_PRESENT:
|
|
{
|
|
for (p_object* p_objp = GET_FIRST(&Ship_arrival_list); p_objp != END_OF_LIST(&Ship_arrival_list); p_objp = GET_NEXT(p_objp))
|
|
{
|
|
if (p_objp->wingnum == WING_INDEX(oswpt.wingp))
|
|
{
|
|
luacpp::LuaValueList args;
|
|
args.push_back(luacpp::LuaValue::createValue(L, l_ParseObject.Set(parse_object_h(p_objp))));
|
|
|
|
body.call(L, args);
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
case OSWPT_TYPE_SHIP_ON_TEAM:
|
|
case OSWPT_TYPE_WHOLE_TEAM:
|
|
{
|
|
for (p_object* p_objp = GET_FIRST(&Ship_arrival_list); p_objp != END_OF_LIST(&Ship_arrival_list); p_objp = GET_NEXT(p_objp))
|
|
{
|
|
if (p_objp->team == oswpt.team)
|
|
{
|
|
luacpp::LuaValueList args;
|
|
args.push_back(luacpp::LuaValue::createValue(L, l_ParseObject.Set(parse_object_h(p_objp))));
|
|
|
|
body.call(L, args);
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
case OSWPT_TYPE_SHIP:
|
|
case OSWPT_TYPE_WING:
|
|
case OSWPT_TYPE_WAYPOINT:
|
|
case OSWPT_TYPE_NONE:
|
|
case OSWPT_TYPE_EXITED:
|
|
default:
|
|
break;
|
|
}
|
|
|
|
return ADE_RETURN_NIL;
|
|
}
|
|
|
|
|
|
}
|
|
}
|