coords = First@Interpreter["StreetAddress"]["14 James Way, Cambridge MA"]; 

For the first part of the question, you can extract and post-process the callout graphics primitives from `ListPlot[Callout[..]]` and use them with `GeoGraphics`:


    GeoGraphics[{Polygon[Entity["City", {"Cambridge", "Massachusetts", "UnitedStates"}]], 
      GeoMarker[coords, Style["\[FilledCircle]", 14, Blue]],
      Cases[ListPlot[{Callout[coords, "Hi", "CalloutStyle" -> Red]}], _GraphicsGroup, All] /. 
         Offset[a_, b_] :> Offset[a, GeoPosition[b]]}]

[![enter image description here][1]][1]

Alternatively, you can use the `CalloutMarker` as the `GeoMarker`:

    GeoGraphics[{Polygon[Entity["City", {"Cambridge", "Massachusetts", "UnitedStates"}]], 
      Cases[ListPlot[{Callout[coords, "Hi", "CalloutStyle" -> Red, 
           CalloutMarker -> "Star"]}], _GraphicsGroup, All] /.
       {Offset[a_, b_] :> Offset[a, GeoPosition[b]], 
        Inset[a_, b_, c__] :> Inset[a, GeoGridPosition[GeoPosition[b], "Mercator"], c]}}]

[![enter image description here][2]][2]


  [1]: https://i.sstatic.net/nfSbM.png
  [2]: https://i.sstatic.net/128Nz.png