Author: sveinung
Date: Thu Mar 17 16:44:21 2016
New Revision: 32261

URL: http://svn.gna.org/viewcvs/freeciv?rev=32261&view=rev
Log:
Metaknowledge evaluation RPT_POSSIBLE mode.

Meta knowledge requirement evaluation considers what information a player
has access to when evaluating a requirement. It can end up returning maybe
when the player don't have the needed information. Up until now it has only
supported the RPT_CERTAIN requirement evaluation mode.

Support the RPT_POSSIBLE requirement evaluation mode in meta knowledge
requirement evaluation.

See patch #7066

Modified:
    branches/S2_6/common/actions.c
    branches/S2_6/common/metaknowledge.c
    branches/S2_6/common/metaknowledge.h

Modified: branches/S2_6/common/actions.c
URL: 
http://svn.gna.org/viewcvs/freeciv/branches/S2_6/common/actions.c?rev=32261&r1=32260&r2=32261&view=diff
==============================================================================
--- branches/S2_6/common/actions.c      (original)
+++ branches/S2_6/common/actions.c      Thu Mar 17 16:44:21 2016
@@ -857,13 +857,13 @@
                                     actor_building, actor_tile,
                                     actor_unit, actor_output,
                                     actor_specialist,
-                                    &enabler->actor_reqs),
+                                    &enabler->actor_reqs, RPT_CERTAIN),
                       mke_eval_reqs(actor_player, target_player,
                                     actor_player, target_city,
                                     target_building, target_tile,
                                     target_unit, target_output,
                                     target_specialist,
-                                    &enabler->target_reqs));
+                                    &enabler->target_reqs, RPT_CERTAIN));
     if (current == TRI_YES) {
       return TRI_YES;
     } else if (current == TRI_MAYBE) {
@@ -898,7 +898,7 @@
                                    target_building, target_tile,
                                    target_unit, target_output,
                                    target_specialist,
-                                   &(peffect->reqs))) {
+                                   &(peffect->reqs), RPT_CERTAIN)) {
       return FALSE;
     }
   } effect_list_iterate_end;

Modified: branches/S2_6/common/metaknowledge.c
URL: 
http://svn.gna.org/viewcvs/freeciv/branches/S2_6/common/metaknowledge.c?rev=32261&r1=32260&r2=32261&view=diff
==============================================================================
--- branches/S2_6/common/metaknowledge.c        (original)
+++ branches/S2_6/common/metaknowledge.c        Thu Mar 17 16:44:21 2016
@@ -188,7 +188,8 @@
                             const struct unit *target_unit,
                             const struct output_type *target_output,
                             const struct specialist *target_specialist,
-                            const struct requirement *req)
+                            const struct requirement *req,
+                            const enum   req_problem_type prob_type)
 {
   fc_assert_ret_val_msg(NULL != pow_player, false, "No point of view");
 
@@ -200,6 +201,12 @@
       || req->source.kind == VUT_MINHP) {
     switch (req->range) {
     case REQ_RANGE_LOCAL:
+      if (target_unit == NULL) {
+        /* The unit may exist but not be passed when the problem type is
+         * RPT_POSSIBLE. */
+        return prob_type == RPT_CERTAIN;
+      }
+
       return target_unit && can_player_see_unit(pow_player, target_unit);
     case REQ_RANGE_CADJACENT:
     case REQ_RANGE_ADJACENT:
@@ -218,6 +225,12 @@
   if (req->source.kind == VUT_UNITSTATE) {
     fc_assert_ret_val_msg(req->range == REQ_RANGE_LOCAL, FALSE, "Wrong range");
 
+    if (target_unit == NULL) {
+      /* The unit may exist but not be passed when the problem type is
+       * RPT_POSSIBLE. */
+      return prob_type == RPT_CERTAIN;
+    }
+
     switch (req->source.value.unit_state) {
     case USP_TRANSPORTED:
     case USP_LIVABLE_TILE:
@@ -233,6 +246,12 @@
 
   if (req->source.kind == VUT_MINMOVES) {
     fc_assert_ret_val_msg(req->range == REQ_RANGE_LOCAL, FALSE, "Wrong range");
+
+    if (target_unit == NULL) {
+      /* The unit may exist but not be passed when the problem type is
+       * RPT_POSSIBLE. */
+      return prob_type == RPT_CERTAIN;
+    }
 
     switch (req->range) {
     case REQ_RANGE_LOCAL:
@@ -256,6 +275,13 @@
   if (req->source.kind == VUT_DIPLREL) {
     switch (req->range) {
     case REQ_RANGE_LOCAL:
+      if (other_player == NULL
+          || target_player == NULL) {
+        /* The two players may exist but not be passed when the problem
+         * type is RPT_POSSIBLE. */
+        return prob_type == RPT_CERTAIN;
+      }
+
       if (pow_player == target_player
           || pow_player == other_player)  {
         return TRUE;
@@ -269,6 +295,12 @@
       /* TODO: Non symmetric diplomatic relationships. */
       break;
     case REQ_RANGE_PLAYER:
+      if (target_player == NULL) {
+        /* The target player may exist but not be passed when the problem
+         * type is RPT_POSSIBLE. */
+        return prob_type == RPT_CERTAIN;
+      }
+
       if (pow_player == target_player) {
         return TRUE;
       }
@@ -300,7 +332,13 @@
     }
   }
 
-  if (req->source.kind == VUT_MINSIZE && target_city != NULL) {
+  if (req->source.kind == VUT_MINSIZE) {
+    if (target_city == NULL) {
+      /* The city may exist but not be passed when the problem type is
+       * RPT_POSSIBLE. */
+      return prob_type == RPT_CERTAIN;
+    }
+
     if (mke_can_see_city_externals(pow_player, target_city)) {
       return TRUE;
     }
@@ -308,6 +346,12 @@
 
   if (req->source.kind == VUT_CITYTILE) {
     struct city *pcity;
+
+    if (target_tile == NULL) {
+      /* The tile may exist but not be passed when the problem type is
+       * RPT_POSSIBLE. */
+      return prob_type == RPT_CERTAIN;
+    }
 
     switch (req->range) {
     case REQ_RANGE_LOCAL:
@@ -384,8 +428,9 @@
     case REQ_RANGE_CITY:
     case REQ_RANGE_LOCAL:
       if (!target_city) {
-        /* Can't be. No city to contain it. */
-        return TRUE;
+        /* RPT_CERTAIN: Can't be. No city to contain it.
+         * RPT_POSSIBLE: A city like that may exist but not be passed. */
+        return prob_type == RPT_CERTAIN;
       }
 
       if (can_player_see_city_internals(pow_player, target_city)) {
@@ -413,25 +458,51 @@
 
   if (req->source.kind == VUT_NATION
       || req->source.kind == VUT_NATIONGROUP) {
+    if (!target_player
+        && (req->range == REQ_RANGE_PLAYER
+            || req->range == REQ_RANGE_TEAM
+            || req->range == REQ_RANGE_ALLIANCE)) {
+      /* The player (that can have a nationality or be alllied to someone
+       * with the nationality) may exist but not be passed when the problem
+       * type is RPT_POSSIBLE. */
+      return prob_type == RPT_CERTAIN;
+    }
+
     return TRUE;
   }
 
   if (req->source.kind == VUT_ADVANCE || req->source.kind == VUT_TECHFLAG) {
-    if (req->range == REQ_RANGE_PLAYER
-        && can_see_techs_of_target(pow_player, target_player)) {
-      return TRUE;
+    if (req->range == REQ_RANGE_PLAYER) {
+      if (!target_player) {
+        /* The player (that may or may not possess the tech) may exist but
+         * not be passed when the problem type is RPT_POSSIBLE. */
+        return prob_type == RPT_CERTAIN;
+      }
+
+      return can_see_techs_of_target(pow_player, target_player);
     }
   }
 
   if (req->source.kind == VUT_GOVERNMENT) {
-    if (req->range == REQ_RANGE_PLAYER
-        && (pow_player == target_player
-            || could_intel_with_player(pow_player, target_player))) {
-      return TRUE;
+    if (req->range == REQ_RANGE_PLAYER) {
+      if (!target_player) {
+        /* The player (that may or may not possess the tech) may exist but
+         * not be passed when the problem type is RPT_POSSIBLE. */
+        return prob_type == RPT_CERTAIN;
+      }
+
+      return (pow_player == target_player
+              || could_intel_with_player(pow_player, target_player));
     }
   }
 
   if (req->source.kind == VUT_MAXTILEUNITS) {
+    if (target_tile == NULL) {
+      /* The tile may exist but not be passed when the problem type is
+       * RPT_POSSIBLE. */
+      return prob_type == RPT_CERTAIN;
+    }
+
     switch (req->range) {
     case REQ_RANGE_LOCAL:
       return can_player_see_hypotetic_units_at(pow_player, target_tile);
@@ -478,6 +549,12 @@
       || req->source.kind == VUT_EXTRAFLAG
       || req->source.kind == VUT_BASEFLAG
       || req->source.kind == VUT_BASEFLAG) {
+    if (target_tile == NULL) {
+      /* The tile may exist but not be passed when the problem type is
+       * RPT_POSSIBLE. */
+      return prob_type == RPT_CERTAIN;
+    }
+
     switch (req->range) {
     case REQ_RANGE_LOCAL:
       return is_tile_seen(pow_player, target_tile);
@@ -536,14 +613,15 @@
              const struct unit *target_unit,
              const struct output_type *target_output,
              const struct specialist *target_specialist,
-             const struct requirement *req)
+             const struct requirement *req,
+             const enum   req_problem_type prob_type)
 {
   const struct unit_type *target_unittype;
 
   if (!is_req_knowable(pow_player, target_player, other_player,
                        target_city, target_building, target_tile,
                        target_unit, target_output,
-                       target_specialist, req)) {
+                       target_specialist, req, prob_type)) {
     return TRI_MAYBE;
   }
 
@@ -555,7 +633,7 @@
 
   if (is_req_active(target_player, other_player, target_city,
                     target_building, target_tile, target_unit, target_unittype,
-                    target_output, target_specialist, req, RPT_CERTAIN)) {
+                    target_output, target_specialist, req, prob_type)) {
     return TRI_YES;
   } else {
     return TRI_NO;
@@ -577,7 +655,8 @@
               const struct unit *target_unit,
               const struct output_type *target_output,
               const struct specialist *target_specialist,
-              const struct requirement_vector *reqs)
+              const struct requirement_vector *reqs,
+              const enum   req_problem_type prob_type)
 {
   enum fc_tristate current;
   enum fc_tristate result;
@@ -587,7 +666,7 @@
     current = mke_eval_req(pow_player, target_player, other_player,
                            target_city, target_building, target_tile,
                            target_unit, target_output,
-                           target_specialist, preq);
+                           target_specialist, preq, prob_type);
     if (current == TRI_NO) {
       return TRI_NO;
     } else if (current == TRI_MAYBE) {

Modified: branches/S2_6/common/metaknowledge.h
URL: 
http://svn.gna.org/viewcvs/freeciv/branches/S2_6/common/metaknowledge.h?rev=32261&r1=32260&r2=32261&view=diff
==============================================================================
--- branches/S2_6/common/metaknowledge.h        (original)
+++ branches/S2_6/common/metaknowledge.h        Thu Mar 17 16:44:21 2016
@@ -34,7 +34,8 @@
              const struct unit *target_unit,
              const struct output_type *target_output,
              const struct specialist *target_specialist,
-             const struct requirement *req);
+             const struct requirement *req,
+             const enum   req_problem_type prob_type);
 
 enum fc_tristate
 mke_eval_reqs(const struct player *pow_player,
@@ -46,7 +47,8 @@
               const struct unit *target_unit,
               const struct output_type *target_output,
               const struct specialist *target_specialist,
-              const struct requirement_vector *reqs);
+              const struct requirement_vector *reqs,
+              const enum   req_problem_type prob_type);
 
 
 bool can_see_techs_of_target(const struct player *pow_player,


_______________________________________________
Freeciv-commits mailing list
Freeciv-commits@gna.org
https://mail.gna.org/listinfo/freeciv-commits

Reply via email to